* Initial support for multiple arguments in rarc2 for ARM
- Some more fixes in the ARM emitter backend - Single quoted strings are now supported, not filtered - Fix math opcode names for ARM - Added support for /**/ and // comments * Fix makefile for test programs in rarc2/t - Added simple hello world for tests in rarc2/t
This commit is contained in:
parent
441456767a
commit
90a2b9f84a
|
@ -1,10 +1,6 @@
|
|||
RCC : Ralang/Relocatable Code Compiler
|
||||
======================================
|
||||
|
||||
TODO:
|
||||
-----
|
||||
add support for /* comments */
|
||||
|
||||
Compiler pipeline: the picture
|
||||
------------------------------
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* pancake // nopcode.org 2010 -- emit module for rcc */
|
||||
/* pancake // nopcode.org 2010 -- arm emiter */
|
||||
|
||||
#include "rarc2.h"
|
||||
|
||||
|
@ -14,6 +14,8 @@
|
|||
|
||||
// no attsyntax for arm
|
||||
static char *regs[] = R_GP;
|
||||
static int lastarg = 0;
|
||||
static char lastargs[16][32];
|
||||
|
||||
static char *emit_syscall (int num) {
|
||||
return strdup (": mov "R_AX", `.arg`\n: svc 0x8000\n");
|
||||
|
@ -64,9 +66,21 @@ static void emit_set_string(const char *dstvar, const char *str, int j) {
|
|||
rcc_printf (".string \"%s\"\n", str);
|
||||
if (rest) rcc_printf (".fill %d, 1, 0\n", (rest));
|
||||
rcc_printf (" sub r0, pc, $%d\n", off+16);
|
||||
{
|
||||
char str[32], *p = mk_var (str, dstvar, 0);
|
||||
//rcc_printf("DSTVAR=%s --> %s\n", dstvar, p);
|
||||
rcc_printf (" str r0, [%s]\n", p);
|
||||
}
|
||||
}
|
||||
|
||||
static void emit_call(const char *str, int atr) {
|
||||
int i;
|
||||
//rcc_printf(" ARGS=%d CALL(%s,%d)\n", lastarg, str, atr);
|
||||
for(i=0;i<lastarg;i++) {
|
||||
rcc_printf (" ldr r%d, [%s]\n", lastarg-1-i, lastargs[i]);
|
||||
lastargs[i][0] = 0;
|
||||
}
|
||||
|
||||
if (atr) {
|
||||
rcc_printf(" ldr r0, %s", str);
|
||||
rcc_printf(" blx r0\n");
|
||||
|
@ -77,11 +91,18 @@ static void emit_arg (int xs, int num, const char *str) {
|
|||
int d = atoi (str);
|
||||
if (!attsyntax && (*str=='$'))
|
||||
str++;
|
||||
// ARGMENTS ONLY IN R0, R1, .. ooh common!
|
||||
return; // XXX
|
||||
lastarg = num;
|
||||
switch (xs) {
|
||||
case 0:
|
||||
rcc_printf (" push {%s}\n", str);
|
||||
if (strchr(str, ',')) {
|
||||
//rcc_printf (". str r0, [%s]\n", str);
|
||||
strncpy (lastargs[num-1], str, sizeof(lastargs[0]));
|
||||
} else {
|
||||
if (!atoi (str)) eprintf ("WARNING: probably a bug?\n");
|
||||
rcc_printf (" mov r0, $%s\n", str);
|
||||
snprintf( lastargs[num-1], sizeof (lastargs[0]), "fp, $-%d", 8+(num*4));
|
||||
rcc_printf (" str r0, [%s]\n", lastargs[num-1]);
|
||||
}
|
||||
break;
|
||||
case '*':
|
||||
rcc_printf (" push {%s}\n", str);
|
||||
|
@ -99,7 +120,8 @@ static void emit_get_result(const char *ocn) {
|
|||
}
|
||||
|
||||
static void emit_restore_stack (int size) {
|
||||
//rcc_printf(" add sp, %d\n", size);
|
||||
// XXX: must die.. or add emit_store_stack. not needed by ARM
|
||||
// rcc_printf(" add sp, %d\n", size);
|
||||
}
|
||||
|
||||
static void emit_get_while_end (char *str, const char *ctxpush, const char *label) {
|
||||
|
@ -115,8 +137,8 @@ static void emit_while_end (const char *labelback) {
|
|||
|
||||
static void emit_get_var (int type, char *out, int idx) {
|
||||
switch (type) {
|
||||
case 0: sprintf (out, "fp,%c%d", idx>0?' ':'+', -idx); break; /* variable */
|
||||
case 1: sprintf (out, "sp,%c%d", idx>0?'+':' ', idx); break; /* argument */
|
||||
case 0: sprintf (out, "fp,$%d", -idx); break; /* variable */
|
||||
case 1: sprintf (out, "sp,$%d", idx); break; /* argument */ // XXX: MUST BE r0, r1, r2, ..
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -180,9 +202,9 @@ static void emit_load(const char *dst, int sz) {
|
|||
static void emit_mathop(int ch, int vs, int type, const char *eq, const char *p) {
|
||||
char *op;
|
||||
switch (ch) {
|
||||
case '^': op = "xor"; break;
|
||||
case '^': op = "eor"; break;
|
||||
case '&': op = "and"; break;
|
||||
case '|': op = "or"; break;
|
||||
case '|': op = "orr"; break;
|
||||
case '-': op = "sub"; break;
|
||||
case '+': op = "add"; break;
|
||||
case '*': op = "mul"; break;
|
||||
|
|
|
@ -181,7 +181,7 @@ static void emit_trap () {
|
|||
|
||||
static void emit_load_ptr(const char *dst) {
|
||||
int d = atoi (dst);
|
||||
eprintf ("HACK HACK HACK\n");
|
||||
//eprintf ("emit_load_ptr: HACK\n");
|
||||
// XXX: 32/64bit care
|
||||
if (attsyntax) rcc_printf (" leal %d(%%"R_BP"), %%"R_AX"\n", d);
|
||||
else rcc_printf (" leal "R_AX", dword ptr ["R_BP"+%d]\n", d);
|
||||
|
|
|
@ -101,11 +101,14 @@ static char *get_frame_label(int type) {
|
|||
return label;
|
||||
}
|
||||
|
||||
static void rcc_pushstr(char *str) {
|
||||
static void rcc_pushstr(char *str, int filter) {
|
||||
int dotrim = 1;
|
||||
int i, j, len;
|
||||
|
||||
emit->comment ("encode string (%s) (%s)", str, callname);
|
||||
emit->comment ("encode %s string (%s) (%s)",
|
||||
filter?"filtered":"unfiltered", str, callname);
|
||||
|
||||
if (filter)
|
||||
for (i=0; str[i]; i++) {
|
||||
if (str[i]=='\\') {
|
||||
switch (str[i+1]) {
|
||||
|
@ -152,7 +155,7 @@ char *mk_var(char *out, const char *_str, int delta) {
|
|||
emit->get_var (0, out, idx-stackfixed);
|
||||
//sprintf(out, "%d(%%"R_BP")", -(atoi(str+4)+delta+R_SZ-stackfixed));
|
||||
} else
|
||||
if (!memcmp(str+1, "var", 3)) {
|
||||
if (!memcmp (str+1, "var", 3)) {
|
||||
emit->get_var (0, out, idx);
|
||||
//sprintf(out, "%d(%%"R_BP")", -(atoi(str+4)+delta+R_SZ));
|
||||
} else
|
||||
|
@ -186,7 +189,8 @@ char *mk_var(char *out, const char *_str, int delta) {
|
|||
ret = str; /* TODO: show error, invalid var name? */
|
||||
eprintf ("FUCKED UP\n");
|
||||
}
|
||||
} else if (str[0]=='"') {
|
||||
} else if (*str=='"' || *str=='\'') {
|
||||
int mustfilter = *str=='"';
|
||||
if (!stackfixed)
|
||||
eprintf ("WARNING: No room in the static stackframe!\n");
|
||||
/* TODO: check for room in stackfixed area */
|
||||
|
@ -195,7 +199,7 @@ char *mk_var(char *out, const char *_str, int delta) {
|
|||
str[len]='\0';
|
||||
sprintf (foo, ".fix%d", nargs*16); /* XXX FIX DELTA !!!1 */
|
||||
dstvar = strdup (foo);
|
||||
rcc_pushstr (str);
|
||||
rcc_pushstr (str, mustfilter);
|
||||
ret = mk_var (out, foo, 0);
|
||||
}
|
||||
//free ((void *)_str);
|
||||
|
@ -288,7 +292,7 @@ static void rcc_element(char *str) {
|
|||
if (!atoi (str)) {
|
||||
if (dstvar == NULL) /* return string */
|
||||
dstvar = strdup (".fix0");
|
||||
rcc_pushstr (str);
|
||||
rcc_pushstr (str, 1);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
|
@ -682,6 +686,10 @@ static int parsechar(char c) {
|
|||
if (oc == '\n')
|
||||
skipline = 1;
|
||||
break;
|
||||
case '/':
|
||||
if (oc == '/')
|
||||
skipline = 1;
|
||||
break;
|
||||
default:
|
||||
elem[elem_n++] = c;
|
||||
}
|
||||
|
|
|
@ -1,11 +1,18 @@
|
|||
LC=../rarc2
|
||||
.PHONY: all clean run top
|
||||
|
||||
RC=../rarc2 -s
|
||||
CC=tcc
|
||||
CC=gcc
|
||||
|
||||
BIN=ptr ret hello shell loop input inline syscall data sub if dump bytedump argv room rawsys
|
||||
BIN=hi ptr ret hello shell loop input inline syscall data sub if dump bytedump argv room rawsys
|
||||
|
||||
all: top ${BIN}
|
||||
|
||||
clean:
|
||||
rm -f ${BIN} *.S
|
||||
|
||||
run:
|
||||
for a in ${BIN}; do ./$$a ; done
|
||||
|
||||
top:
|
||||
#rm -f shell
|
||||
|
@ -13,71 +20,69 @@ top:
|
|||
cd .. && ${MAKE} rarc2
|
||||
|
||||
syscall:
|
||||
${LC} syscall.r > syscall.S
|
||||
${RC} syscall.r > syscall.S
|
||||
${CC} syscall.S -o syscall
|
||||
|
||||
hi:
|
||||
${RC} hi.r > hi.S
|
||||
${CC} hi.S -o hi
|
||||
|
||||
rawsys:
|
||||
${LC} rawsys.r > rawsys.S
|
||||
${RC} rawsys.r > rawsys.S
|
||||
${CC} rawsys.S -o rawsys
|
||||
|
||||
data:
|
||||
${LC} data.r > data.S
|
||||
${RC} data.r > data.S
|
||||
${CC} data.S -o data
|
||||
|
||||
ret:
|
||||
${LC} ret.r > ret.S
|
||||
${RC} ret.r > ret.S
|
||||
${CC} ret.S -o ret
|
||||
|
||||
sub:
|
||||
${LC} sub.r > sub.S
|
||||
${RC} sub.r > sub.S
|
||||
${CC} sub.S -o sub
|
||||
|
||||
inline:
|
||||
${LC} inline.r > inline.S
|
||||
${RC} inline.r > inline.S
|
||||
${CC} inline.S -o inline
|
||||
|
||||
loop:
|
||||
${LC} loop.r > loop.S
|
||||
${RC} loop.r > loop.S
|
||||
${CC} loop.S -o loop
|
||||
|
||||
shell:
|
||||
${LC} shell.r > shell.S
|
||||
${RC} shell.r > shell.S
|
||||
${CC} shell.S -o shell
|
||||
|
||||
hello:
|
||||
${LC} hello.r > hello.S
|
||||
${RC} hello.r > hello.S
|
||||
${CC} -g hello.S -o hello
|
||||
|
||||
ptr:
|
||||
${LC} ptr.r > ptr.S
|
||||
${RC} ptr.r > ptr.S
|
||||
${CC} ptr.S -o ptr
|
||||
|
||||
input:
|
||||
${LC} input.r > input.S
|
||||
${RC} input.r > input.S
|
||||
${CC} input.S -o input
|
||||
|
||||
if:
|
||||
${LC} if.r > if.S
|
||||
${RC} if.r > if.S
|
||||
${CC} if.S -o if
|
||||
|
||||
dump:
|
||||
${LC} dump.r > dump.S
|
||||
${RC} dump.r > dump.S
|
||||
${CC} dump.S -o dump
|
||||
|
||||
bytedump:
|
||||
${LC} bytedump.r > bytedump.S
|
||||
${RC} bytedump.r > bytedump.S
|
||||
${CC} bytedump.S -o bytedump
|
||||
|
||||
argv:
|
||||
${LC} argv.r > argv.S
|
||||
${RC} argv.r > argv.S
|
||||
${CC} argv.S -o argv
|
||||
|
||||
room:
|
||||
${LC} room.r > room.S
|
||||
${RC} room.r > room.S
|
||||
${CC} room.S -o room
|
||||
|
||||
clean:
|
||||
rm -f ${BIN} *.S
|
||||
|
||||
run:
|
||||
for a in ${BIN}; do ./$$a ; done
|
||||
|
|
|
@ -0,0 +1,3 @@
|
|||
main@global(,32) {
|
||||
printf("Hello World\n");
|
||||
}
|
Loading…
Reference in New Issue