commit fd1b69bdb18359773bf43ebea4fbe693c72aa542
parent 7741d58782520663fdc12c27a0c10b795b8d7fad
Author: Roberto E. Vargas Caballero <k0ga@shike2.com>
Date: Sun, 30 Mar 2014 22:41:15 +0200
Emit code for arrays
This code generates a first version of how the code for arrays is
generated.
Diffstat:
M | cc.h | | | 7 | +++++-- |
M | code.c | | | 43 | ++++++++++++++++++++++++++++++++++++++++--- |
M | expr.c | | | 12 | ++++++------ |
M | stmt.c | | | 7 | +++---- |
4 files changed, 54 insertions(+), 15 deletions(-)
diff --git a/cc.h b/cc.h
@@ -215,11 +215,14 @@ enum {
OCAST, OPTR, OADD, OARY
};
-extern void emitsym(Node *), emitunary(Node *), emitbin(Node *);
+extern void
+ emitsym(Node *), emitunary(Node *),
+ emitbin(Node *), emitexp(Node *);
+
extern Node
*node(Inst code, Type *tp, union unode u, uint8_t nchilds),
*unarycode(char op, Type *tp, Node *child),
- *bincode(char op, Node *np1, Node *np2);
+ *bincode(char op, Type *tp, Node *np1, Node *np2);
#define SYM(s) ((union unode) {.sym = s})
#define OP(s) ((union unode) {.op = s})
diff --git a/code.c b/code.c
@@ -4,6 +4,12 @@
#include "cc.h"
+char *opcodes[] = {
+ [OADD] = "+",
+ [OARY] = "'",
+ [OPTR] = "@"
+};
+
Node *
node(Inst code, Type *tp, union unode u, uint8_t nchilds)
{
@@ -25,9 +31,9 @@ unarycode(char op, Type *tp, Node *child)
}
Node *
-bincode(char op, Node *np1, Node *np2)
+bincode(char op, Type *tp, Node *np1, Node *np2)
{
- Node *np = node(emitbin, np1->type, OP(op), 2);
+ Node *np = node(emitbin, tp, OP(op), 2);
np->childs[0] = np1;
np->childs[1] = np2;
return np;
@@ -44,7 +50,7 @@ emitsym(Node *np)
else if (sym->s.isstatic)
c = 'T';
else if (sym->s.isregister)
- c = 'R';
+ c = 'Q';
else
c = 'A';
printf("\t%c%d", c, sym->id);
@@ -53,11 +59,42 @@ emitsym(Node *np)
void
emitunary(Node *np)
{
+ Node *child;
+ char op, letter;
+
+ letter = np->type->letter;
+ child = np->childs[0];
+ (*child->code)(child);
+ switch (op = np->u.op) {
+ case OCAST:
+ printf("\t%c%c", child->type->letter, letter);
+ break;
+ case OARY:
+ fputs("\t'", stdout);
+ break;
+ default:
+ printf("\t%s%c", opcodes[op], letter);
+ break;
+ }
}
void
emitbin(Node *np)
{
+ Node *child1, *child2;
+
+ child1 = np->childs[0];
+ child2 = np->childs[1];
+ (*child1->code)(child1);
+ (*child2->code)(child2);
+ printf("\t%s%c", opcodes[np->u.op], np->type->letter);
+}
+
+void
+emitexp(Node *np)
+{
+ (*np->code)(np);
+ putchar('\n');
}
void
diff --git a/expr.c b/expr.c
@@ -52,7 +52,7 @@ add(Node *np1, Node *np2)
Type *tp1, *tp2;
uint8_t t1, t2, taux;
- tp1 = UNQUAL(np1->type), tp2 = UNQUAL(np1->type);
+ tp1 = UNQUAL(np1->type), tp2 = UNQUAL(np2->type);
t1 = tp1->op, t2 = tp2->op;
switch (t1) {
@@ -87,17 +87,17 @@ int_float: np2 = unarycode(OCAST, np1->type, np2);
}
break;
case PTR: case FTN: case ARY:
-pointer: if (t1 == PTR)
- np1 = unarycode(OPTR, np1->type, np1);
+pointer: if (t1 == ARY)
+ tp1 = mktype(tp1->type, PTR, NULL, 0);
if (t2 != INT)
goto incorrect;
- np2 = unarycode(OCAST, np1->type, np2);
+ np2 = unarycode(OCAST, tp1, np2);
break;
default:
goto incorrect;
}
- return bincode(OADD, np1, np2);
+ return bincode(OADD, tp1, np1, np2);
incorrect:
error("incorrect arithmetic operands"); /*TODO: print type names */
@@ -117,7 +117,7 @@ array(Node *np1, Node *np2)
if (t1 != INT && t2 != INT)
goto bad_subs;
np1 = add(np1, np2);
- return unarycode(OARY, UNQUAL(np1->type)->type , np1);
+ return unarycode(OARY, np1->type->type , np1);
bad_vector:
err = "subscripted value is neither array nor pointer nor vector";
diff --git a/stmt.c b/stmt.c
@@ -8,6 +8,7 @@ void
compound(void)
{
extern void decl(void);
+ extern Node *expr(void);
expect('{');
while (!accept('}')) {
@@ -16,9 +17,8 @@ compound(void)
decl();
break;
default:
- expr();
- /* TODO: Evaluate the expression here */
+ emitexp(expr());
}
expect(';');
}
-}
-\ No newline at end of file
+}