lli

A small emulated asm like lang
Log | Files | Refs

commit 47e635186720d4bcf9e6d9577659b2f509facc53
parent d6c5ae7743c00874b4b9a392dba3a1220c04612e
Author: thing1 <l.standen@posteo.com>
Date:   Fri,  3 Oct 2025 13:15:50 +0100

added a call stack

Diffstat:
Mexamples/Makefile | 9+++++----
Mexamples/callstack.ll | 5+++--
Aexamples/print.ll | 12++++++++++++
Mlli.c | 57+++++++++++++++++++++++++++++++++++++++++++++++++++++----
Mlli.h | 11+++++++++++
Mlliasm.c | 24++++++++++++++++++++++--
6 files changed, 106 insertions(+), 12 deletions(-)

diff --git a/examples/Makefile b/examples/Makefile @@ -1,12 +1,13 @@ -all: cat loadprog +all: cat loadprog callstack print cat: cat.ll lliasm cat.ll cat.rom loadprog: loadprog.ll lliasm loadprog.ll loadprog.rom - -run: all - lli ./cat.rom +callstack: callstack.ll + lliasm callstack.ll callstack.rom +print: print.ll + lliasm print.ll print.rom clean: rm -rf *.rom diff --git a/examples/callstack.ll b/examples/callstack.ll @@ -1,9 +1,10 @@ |0x0 @stdin |0x1 @stdout |0x2 @stderr +|0x20 @str "hello 0 |0x100 @tester -p65 &stdout storeb +&str loadb &stdout storeb ret |0x1000 -call &tester +&tester call halt diff --git a/examples/print.ll b/examples/print.ll @@ -0,0 +1,12 @@ +|0x0 @stdin |0x1 @stdout |0x2 @stderr +|0x10 @str "hello 0 + +|0x100 @print +dupi +loadb &stdout storeb +p1 add +&print jmp + +|0x1000 +&str &print call +halt diff --git a/lli.c b/lli.c @@ -17,7 +17,7 @@ type peek_##type(stack *s) {\ if (s->sptr == s->arr) \ errormsg("Stack underflow"); \ - return *(type *)s->sptr; \ + return *(type *)(s->sptr - sizeof(type)); \ } @@ -56,13 +56,13 @@ lliexec() { .cap = 512, .arr = malloc(512), }; - cs.sptr = s.arr; + cs.sptr = cs.arr; step: uint8_t opcode = *(uint8_t *)pc, val8; uint16_t val16; - uint32_t loc, val32; + uint32_t loc, val32, operand1, operand2; switch (opcode) { @@ -99,6 +99,26 @@ step: onwrite_unix_memio(&memory[0x0]); break; + case DUPB: + case DUPS: + case DUPI: + switch (opcode) { + case DUPB: + val8 = peek_uint8_t(&s); + push_uint8_t(&s, &val8); + break; + case DUPS: + val16 = peek_uint16_t(&s); + push_uint16_t(&s, &val16); + break; + case DUPI: + val32 = peek_uint32_t(&s); + push_uint32_t(&s, &val32); + break; + } + break; + + case JMP: loc = pop_uint32_t(&s); pc = &memory[loc]; @@ -106,7 +126,8 @@ step: case CALL: loc = pop_uint32_t(&s); - push_uint32_t(&cs, (uint32_t *)(pc - &memory[0])); + val32 = (pc - &memory[0]) + 1; + push_uint32_t(&cs, &val32); pc = &memory[loc]; goto step; case RET: @@ -120,6 +141,34 @@ step: pc += sizeof(uint32_t); goto step; + case ADD: + operand2 = pop_uint32_t(&s); + operand1 = pop_uint32_t(&s); + val32 = operand1 + operand2; + push_uint32_t(&s, &val32); + break; + + case SUB: + operand2 = pop_uint32_t(&s); + operand1 = pop_uint32_t(&s); + val32 = operand1 - operand2; + push_uint32_t(&s, &val32); + break; + + case DIV: + operand2 = pop_uint32_t(&s); + operand1 = pop_uint32_t(&s); + val32 = operand1 / operand2; + push_uint32_t(&s, &val32); + break; + + case MUL: + operand2 = pop_uint32_t(&s); + operand1 = pop_uint32_t(&s); + val32 = operand1 * operand2; + push_uint32_t(&s, &val32); + break; + case HALT: goto end; case DELB: pop_uint8_t(&s); break; case DELS: pop_uint16_t(&s); break; diff --git a/lli.h b/lli.h @@ -21,12 +21,23 @@ typedef enum ttype { STORES, STOREI, + DUPB, + DUPS, + DUPI, + LOADB, LOADS, LOADI, + ADD, + SUB, + DIV, + MUL, + JMP, + JMPZ, CALL, + CALLZ, RET, HALT, } ttype; diff --git a/lliasm.c b/lliasm.c @@ -132,13 +132,33 @@ tokenize(char *word, int *size) { else if (SAME(word, "storeb")) val->type = STOREB; + else if (SAME(word, "dupi")) + val->type = DUPI; + else if (SAME(word, "dups")) + val->type = DUPS; + else if (SAME(word, "dupb")) + val->type = DUPB; + else if (SAME(word, "jmp")) val->type = JMP; + else if (SAME(word, "jmpz")) + val->type = JMPZ; else if (SAME(word, "call")) - val->type = JMP; + val->type = CALL; + else if (SAME(word, "callz")) + val->type = CALLZ; else if (SAME(word, "ret")) - val->type = JMP; + val->type = RET; + + else if (SAME(word, "add")) + val->type = ADD; + else if (SAME(word, "sub")) + val->type = SUB; + else if (SAME(word, "div")) + val->type = DIV; + else if (SAME(word, "mul")) + val->type = MUL; else if (SAME(word, "halt")) val->type = HALT;