ruka_codegen_wasm/memory_and_release/
alloc.rs1use super::*;
2
3pub(crate) fn emit_heap_alloc(
4 body: &mut walrus::InstrSeqBuilder,
5 runtime: &RuntimeFunctions,
6 size_bytes: i32,
7 kind_id: i32,
8 source_pos: Option<ruka_mir::MirSourcePos>,
9 fallback_line: i32,
10 dst_local: LocalId,
11) -> Result<(), LowerError> {
12 let alloc = runtime_tracked_alloc_function(runtime)?;
13 let (kind_id, file_id, line, column) = alloc_site_parts(kind_id, source_pos, fallback_line);
14 body.i32_const(size_bytes)
15 .i32_const(kind_id)
16 .i32_const(file_id)
17 .i32_const(line)
18 .i32_const(column)
19 .call(alloc.function_id)
20 .local_set(dst_local);
21 Ok(())
22}
23
24pub(crate) fn emit_copy_bytes(
25 body: &mut walrus::InstrSeqBuilder,
26 memory_id: MemoryId,
27 src_ptr_local: LocalId,
28 dst_ptr_local: LocalId,
29 size: u32,
30 scratch_i32_local: LocalId,
31 _scratch_i32_local_b: LocalId,
32) -> Result<(), LowerError> {
33 let size_i32 = int32_from_u32(size, "copy byte size")?;
34 body.i32_const(0).local_set(scratch_i32_local);
35 body.block(None, |done| {
36 let done_id = done.id();
37 done.loop_(None, |loop_| {
38 let loop_id = loop_.id();
39 loop_
40 .local_get(scratch_i32_local)
41 .i32_const(size_i32)
42 .binop(BinaryOp::I32GeU)
43 .br_if(done_id)
44 .local_get(dst_ptr_local)
45 .local_get(scratch_i32_local)
46 .binop(BinaryOp::I32Add)
47 .local_get(src_ptr_local)
48 .local_get(scratch_i32_local)
49 .binop(BinaryOp::I32Add)
50 .instr(Load {
51 memory: memory_id,
52 kind: LoadKind::I32_8 {
53 kind: walrus::ir::ExtendedLoad::ZeroExtend,
54 },
55 arg: MemArg {
56 align: 1,
57 offset: 0,
58 },
59 })
60 .instr(Store {
61 memory: memory_id,
62 kind: StoreKind::I32_8 { atomic: false },
63 arg: MemArg {
64 align: 1,
65 offset: 0,
66 },
67 })
68 .local_get(scratch_i32_local)
69 .i32_const(1)
70 .binop(BinaryOp::I32Add)
71 .local_set(scratch_i32_local)
72 .br(loop_id);
73 });
74 });
75 Ok(())
76}