shithub: scc

Download patch

ref: 828528f9e6b85837d6b804aac5cbc18f97116bfb
parent: ed9dc0fc53e6c6073a55941f41b4c4d907547364
parent: b6b38357b4e631ba81d71e372dadc5e9511f4f78
author: Roberto E. Vargas Caballero <[email protected]>
date: Thu Sep 18 15:46:51 EDT 2014

Merge branch 'bsc'

--- a/cc2/cc2.h
+++ b/cc2/cc2.h
@@ -87,6 +87,7 @@
 #define ONE       '!'
 #define OOR       'o'
 #define OAND      'y'
+#define OCAST     'c'
 #define ONEG      '_'
 #define OCPL      '~'
 #define OCOMMA    ','
--- a/cc2/cgen.c
+++ b/cc2/cgen.c
@@ -16,16 +16,17 @@
 };
 
 enum {
-	A, B, C, D, E, H, L, IYL, IYH, NREGS, IXL, IXH, F, I, SP, AF, HL, DE, BC, IX, IY
+	A = 1, B, C, D, E, H, L, IYL, IYH, NREGS,
+	IXL, IXH, F, I, SP, AF, HL, DE, BC, IX, IY
 };
 
-char *opnames[] = {
+static char *opnames[] = {
 	[PUSH] = "PUSH", [POP] = "POP", [LD]  = "LD", [ADD] = "ADD",
 	[RET]  = "RET" , [ADDI]= "ADD", [LDI] = "LD", [ADDX] = "ADD",
 	[ADCX] = "ADC" , [LDX] = "LD" , [LDFX] = "LD"
 };
 
-char *regnames[] = {
+static char *regnames[] = {
 	[AF] = "AF", [HL] = "HL", [DE] = "DE", [BC] = "BC", [IX] = "IX",
 	[IY] = "IY", [SP] = "SP", [A]  = "A",  [F]  = "F",  [B]  = "B",
 	[C]  = "C",  [D]  = "D",  [E]  = "E",  [H]  = "H",  [L]  = "L",
@@ -32,6 +33,10 @@
 	[IXL]= "IXL",[IXH]= "IXH",[IYL]= "IYL",[IYH]= "IYH", [I] = "I"
 };
 
+static bool reguse[NREGS];
+static char upper[] = {[DE] = D, [HL] = H, [BC] = B, [IX] = IXH, [IY] = IYH};
+static char lower[] = {[DE] = E, [HL] = L, [BC] = C, [IX] = IXL, [IY] = IYL};
+
 void
 emit(char op, ...)
 {
@@ -61,7 +66,7 @@
 		imm = va_arg(va, int);
 		printf("\t%s\t%s,%d\n", opnames[op], regnames[reg1], imm);
 		break;
-	case LDFX:
+	case ADDX: case ADCX: case LDFX:
 		reg1 = va_arg(va, int);
 		reg2 = va_arg(va, int);
 		off = va_arg(va, int);
@@ -75,13 +80,6 @@
 		printf("\t%s\t(%s%+d),%s\n",
 		       opnames[op], regnames[reg1], off, regnames[reg2]);
 		break;
-	case ADDX: case ADCX:
-		reg1 = va_arg(va, int);
-		reg2 = va_arg(va, int);
-		off = va_arg(va, int);
-		printf("\t%s\t%s,(%s%+d)\n",
-		       opnames[op], regnames[reg1], regnames[reg2], off);
-		break;
 	case ADDR:
 		label = va_arg(va, char *);
 		printf("%s:\n", label);
@@ -92,60 +90,34 @@
 }
 
 static char
-upper(char pair)
-{
-	switch (pair) {
-	case HL: return H;
-	case BC: return B;
-	case DE: return D;
-	case IY: return IYH;
-	}
-}
-
-static char
-lower(char pair)
-{
-	switch (pair) {
-	case HL: return L;
-	case DE: return E;
-	case BC: return B;
-	case IY: return IYL;
-	}
-}
-
-static char
 allocreg(Node *np)
 {
-	static bool regs[NREGS], *bp;
+	char reg8[] = {A, B, C, D, E, H, L, IYL, IY, 0};
+	char reg16[] = {BC, HL, DE, IY, 0};
+	char *bp, c;
 
 	switch (np->type->size) {
 	case 1:
-		for (bp = regs; bp < &regs[NREGS]; ++bp) {
-			if (*bp)
+		for (bp = reg8; (c = *bp); ++bp) {
+			if (reguse[c])
 				continue;
-			*bp = 1;
-			return bp - regs;
+			reguse[c] = 1;
+			return c;
 		}
 		/* TODO: Move variable to stack using PUSH/POP */
 		break;
 	case 2:
-		if (!regs[H] && !regs[L]) {
-			regs[H] = regs [L] = 1;
-			return HL;
+		for (bp = reg16; (c = *bp); ++bp) {
+			char u = upper[c], l = lower[c];
+
+			if (reguse[u] || reguse[l])
+				continue;
+			reguse[l] = 1;
+			reguse[u];
+			return c;
 		}
-		if (!regs[D] && !regs[E]) {
-			regs[D] = regs [E] = 1;
-			return DE;
-		}
-		if (!regs[C] && !regs[B]) {
-			regs[B] = regs [C] = 1;
-			return BC;
-		}
-		if (!regs[IYL] && !regs[IYH]) {
-			regs[IYL] = regs [IYH] = 1;
-			return IY;
-		}
 		/* TODO: Move variable to stack using PUSH/POP */
+		break;
 	}
 	abort();
 }
@@ -164,11 +136,11 @@
 		sym = np->u.sym;
 		switch (tp->size) {
 		case 1:
-			emit(LDFX, reg, sym->u.v.off);
+			emit(LDFX, reg, IX, sym->u.v.off);
 			break;
 		case 2:
-			emit(LDFX, lower(reg), IX, sym->u.v.off);
-			emit(LDFX, upper(reg), IX, sym->u.v.off+1);
+			emit(LDFX, lower[reg], IX, sym->u.v.off);
+			emit(LDFX, upper[reg], IX, sym->u.v.off+1);
 			break;
 		case 4:
 		case 8:
@@ -246,13 +218,13 @@
 				conmute(np);
 				lp = np->left;
 				rp = np->right;
-			} else if (lp->u.reg != HL || lp->u.reg != IY) {
+			} else if (lp->u.reg != HL && lp->u.reg != IY) {
 				/* TODO: Move HL to variable */
 				emit(PUSH, HL);
-				emit(LD, H, upper(lp->u.reg));
-				emit(LD, L, lower(lp->u.reg));
+				emit(LD, H, upper[lp->u.reg]);
+				emit(LD, L, lower[lp->u.reg]);
 			}
-			emit(ADD, HL, rp->u.reg);
+			emit(ADD, lp->u.reg, rp->u.reg);
 			break;
 		case 4:
 		case 8:
--- a/cc2/parser.c
+++ b/cc2/parser.c
@@ -292,7 +292,33 @@
 	push(np);
 }
 
+static void
+cast(char *token)
+{
+	Node *np = newnode();
+
+	np->right = NULL;
+	np->left = pop();
+	np->op = OCAST;
+	np->type = gettype(token+1);
+	push(np);
+}
+
 static void (*optbl[])(char *) = {
+	[L_INT8] = cast,
+	[L_INT16] = cast,
+	[L_INT32] = cast,
+	[L_INT64] = cast,
+	[L_UINT8] = cast,
+	[L_UINT16] = cast,
+	[L_UINT32] = cast,
+	[L_UINT64] = cast,
+	[L_BOOL] = cast,
+	[L_FLOAT] = cast,
+	[L_DOUBLE] = cast,
+	[L_LDOUBLE] = cast,
+	[L_POINTER] = cast,
+	[L_VOID] = cast,
 	['+'] = operator,
 	['%'] = operator,
 	['-'] = operator,