Line | Branch | Exec | Source |
---|---|---|---|
1 | #include "gwion_util.h" | ||
2 | #include "gwion_ast.h" | ||
3 | #include "gwion_env.h" | ||
4 | #include "vm.h" | ||
5 | #include "instr.h" | ||
6 | #include "emit.h" | ||
7 | #include "gwion.h" | ||
8 | #include "memoize.h" | ||
9 | |||
10 | struct Memoize_ { | ||
11 | struct Vector_ v; | ||
12 | m_uint arg_sz; | ||
13 | m_uint ret_sz; | ||
14 | size_t limit; | ||
15 | size_t curr; | ||
16 | }; | ||
17 | |||
18 | 1 | Memoize memoize_ini(const Emitter emit, const Func f) { | |
19 | 1 | const Memoize m = mp_calloc(emit->gwion->mp, Memoize); | |
20 | 1 | vector_init(&m->v); | |
21 | 1 | m->ret_sz = f->def->base->ret_type->size; | |
22 | 1 | m->arg_sz = f->def->stack_depth; | |
23 | 1 | m->limit = f->memoize; | |
24 | 1 | return m; | |
25 | } | ||
26 | |||
27 | 1 | void memoize_end(MemPool p, const Memoize m) { | |
28 |
2/2✓ Branch 1 taken 3 times.
✓ Branch 2 taken 1 times.
|
4 | for (m_uint i = 0; i < vector_size(&m->v); ++i) |
29 | 3 | mp_free2(p, m->arg_sz + m->arg_sz, (void *)vector_at(&m->v, i)); | |
30 | 1 | vector_release(&m->v); | |
31 | 1 | mp_free(p, Memoize, m); | |
32 | 1 | } | |
33 | |||
34 | 35 | ANN static inline m_bit *get_data(MemPool mp, const Memoize m) { | |
35 |
2/2✓ Branch 1 taken 32 times.
✓ Branch 2 taken 3 times.
|
35 | if (vector_size(&m->v) >= m->limit) |
36 | 32 | return (m_bit *)vector_at(&m->v, m->curr++ % m->limit); | |
37 | 3 | m_bit *data = mp_calloc2(mp, m->arg_sz + m->ret_sz); | |
38 | 3 | vector_add(&m->v, (vtype)data); | |
39 | 3 | return data; | |
40 | } | ||
41 | |||
42 | 35 | INSTR(MemoizeStore) { | |
43 | 35 | const Memoize m = shred->code->memoize; | |
44 | 35 | m_bit *const data = get_data(shred->info->mp, m); | |
45 | 35 | memcpy(data, shred->mem, m->arg_sz); | |
46 | 35 | memcpy(data + m->arg_sz, shred->reg - m->ret_sz, m->ret_sz); | |
47 | 35 | } | |
48 | |||
49 | 99 | INSTR(MemoizeIni) { | |
50 | 99 | const m_uint idx = *(m_uint *)MEM(instr->m_val); | |
51 | 99 | const Memoize m = shred->code->memoize; | |
52 |
2/2✓ Branch 0 taken 79 times.
✓ Branch 1 taken 20 times.
|
99 | if (idx < VLEN(&m->v)) { |
53 | 79 | const m_bit *data = (m_bit *)vector_at(&m->v, idx); | |
54 | 79 | memcpy(MEM(instr->m_val + SZ_INT * 2), data, instr->m_val2); | |
55 | } else | ||
56 | 20 | shred->pc = *(m_uint *)MEM(instr->m_val + SZ_INT); | |
57 | 99 | } | |
58 |