[hackers] [scc] Emit compound initializers || Roberto E. Vargas Caballero

From: <git_AT_suckless.org>
Date: Mon, 18 Jan 2016 17:51:56 +0100 (CET)

commit 43a3b37a514e390199668bab42c3451901de5917
Author: Roberto E. Vargas Caballero <k0ga_AT_shike2.com>
AuthorDate: Mon Jan 18 15:20:50 2016 +0100
Commit: Roberto E. Vargas Caballero <k0ga_AT_shike2.com>
CommitDate: Mon Jan 18 16:34:11 2016 +0100

    Emit compound initializers
    
    At this point we are not emiting anything, but we have the full process
    working. We have to create a function which could emit this kind of
    constants.

diff --git a/cc1/cc1.h b/cc1/cc1.h
index b6f1d4e..84bd68a 100644
--- a/cc1/cc1.h
+++ b/cc1/cc1.h
_AT_@ -384,7 +384,7 @@ extern Node *castcode(Node *np, Type *newtp);
 extern TUINT ones(int nbytes);
 
 /* expr.c */
-extern Node *decay(Node *), *negate(Node *np), *assign(Node *np);;
+extern Node *decay(Node *), *negate(Node *np), *assign(void);;
 extern Node *convert(Node *np, Type *tp1, char iscast);
 extern Node *iconstexpr(void), *condexpr(void), *expr(void);
 extern bool isnodecmp(int op);
diff --git a/cc1/code.c b/cc1/code.c
index d72e5f1..884223b 100644
--- a/cc1/code.c
+++ b/cc1/code.c
_AT_@ -207,6 +207,8 @@ emitconst(Node *np)
                 for (bp = sym->u.s; c = *bp; ++bp)
                         printf("%02X", c & 0xFF);
                 break;
+ case STRUCT:
+ return;
         default:
                 /* TODO: Handle other kind of constants */
                 abort();
diff --git a/cc1/decl.c b/cc1/decl.c
index 2844540..6453649 100644
--- a/cc1/decl.c
+++ b/cc1/decl.c
_AT_@ -788,7 +788,7 @@ identifier(struct decl *dcl)
 
         if (sym->token == IDEN && sym->type->op != FTN)
                 emit(ODECL, sym);
- if (yytoken == '=')
+ if (accept('='))
                 initializer(sym, sym->type, -1);
         if (!(sym->flags & (ISGLOBAL|ISEXTERN)) && tp->op != FTN)
                 sym->flags |= ISDEFINED;
diff --git a/cc1/expr.c b/cc1/expr.c
index 262f261..b20640c 100644
--- a/cc1/expr.c
+++ b/cc1/expr.c
_AT_@ -512,9 +512,7 @@ static Node *
 assignop(char op, Node *lp, Node *rp)
 {
         if ((rp = convert(decay(rp), lp->type, 0)) == NULL) {
- errorp((op == OINIT) ?
- "incorrect initiliazer" :
- "incompatible types when assigning");
+ errorp("incompatible types when assigning");
                 return lp;
         }
 
_AT_@ -657,7 +655,7 @@ arguments(Node *np)
         toomany = 0;
 
         do {
- arg = decay(assign(NULL));
+ arg = decay(assign());
                 argtype = *targs;
                 if (argtype == ellipsistype) {
                         n = 0;
_AT_@ -1006,21 +1004,15 @@ ternary(void)
 }
 
 Node *
-assign(Node *np)
+assign(void)
 {
- Node *(*fun)(char , Node *, Node *);
+ Node *np, *(*fun)(char , Node *, Node *);
         char op;
 
- if (np) {
- op = OINIT;
- } else {
- op = OASSIGN;
- np = ternary();
- }
-
+ np = ternary();
         for (;;) {
                 switch (yytoken) {
- case '=': /* op = op; */; fun = assignop; break;
+ case '=': op = OASSIGN; fun = assignop; break;
                 case MUL_EQ: op = OA_MUL; fun = arithmetic; break;
                 case DIV_EQ: op = OA_DIV; fun = arithmetic; break;
                 case MOD_EQ: op = OA_MOD; fun = integerop; break;
_AT_@ -1035,7 +1027,7 @@ assign(Node *np)
                 }
                 chklvalue(np);
                 next();
- np = (fun)(op, np, assign(NULL));
+ np = (fun)(op, np, assign());
         }
 }
 
_AT_@ -1073,9 +1065,9 @@ expr(void)
 {
         Node *lp, *rp;
 
- lp = assign(NULL);
+ lp = assign();
         while (accept(',')) {
- rp = assign(NULL);
+ rp = assign();
                 lp = node(OCOMMA, rp->type, lp, rp);
         }
 
diff --git a/cc1/init.c b/cc1/init.c
index c5895ee..eb77cd3 100644
--- a/cc1/init.c
+++ b/cc1/init.c
_AT_@ -78,11 +78,24 @@ designation(Init *ip)
         return ip;
 }
 
+static Node *initlist(Type *tp);
+
 static Node *
-initlist(Symbol *sym, Type *tp)
+initialize(Type *tp)
+{
+ Node *np;
+
+ np = (accept('{')) ? initlist(tp) : assign();
+ if ((np = convert(decay(np), tp, 0)) == NULL)
+ errorp("incorrect initializer");
+ return np;
+}
+
+static Node *
+initlist(Type *tp)
 {
         Init *ip;
- Symbol *nsym;
+ Symbol *sym;
         struct designator *dp;
         int toomany = 0;
         Type *newtp;
_AT_@ -99,19 +112,20 @@ initlist(Symbol *sym, Type *tp)
                 designation(ip);
                 switch (tp->op) {
                 case ARY:
- newtp = tp->type;
- if (!tp->defined || ip->pos < tp->n.elem)
+ newtp = sym->type;
+ if (!tp->defined || ip->pos <= tp->n.elem)
                                 break;
                         if (!toomany)
                                 warn("excess elements in array initializer");
                         toomany = 1;
                         break;
                 case STRUCT:
- if (ip->pos < tp->n.elem) {
- sym = tp->p.fields[ip->pos];
+ if (ip->pos <= tp->n.elem) {
+ sym = tp->p.fields[ip->pos-1];
                                 newtp = sym->type;
                                 break;
                         }
+ newtp = inttype;
                         if (!toomany)
                                 warn("excess elements in struct initializer");
                         toomany = 1;
_AT_@ -119,7 +133,7 @@ initlist(Symbol *sym, Type *tp)
                 default:
                         newtp = tp;
                         warn("braces around scalar initializer");
- if (ip->pos <= 0)
+ if (ip->pos == 1)
                                 break;
                         if (!toomany)
                                 warn("excess elements in scalar initializer");
_AT_@ -128,8 +142,7 @@ initlist(Symbol *sym, Type *tp)
                 }
                 dp = ip->head;
                 dp->pos = ip->pos;
- /* TODO: pass the correct parameters to initlist */
- dp->expr = (accept('{')) ? initlist(sym, tp) : assign(NULL);
+ dp->expr = initialize(newtp);
 
                 if (!accept(','))
                         break;
_AT_@ -141,9 +154,10 @@ end_of_initializer:
                 tp->n.elem = ip->pos;
                 tp->defined = 1;
         }
- nsym = newsym(NS_IDEN);
- nsym->u.init = ip;
- return constnode(nsym);
+ sym = newsym(NS_IDEN);
+ sym->u.init = ip;
+ sym->type = tp;
+ return constnode(sym);
 }
 
 void
_AT_@ -155,14 +169,7 @@ initializer(Symbol *sym, Type *tp, int nelem)
         if (tp->op == FTN)
                 errorp("function '%s' is initialized like a variable", sym->name);
 
- switch (yytoken) {
- case '{':
- initlist(sym, tp);
- return;
- case '=':
- np = assign(varnode(sym));
- break;
- }
+ np = node(OINIT, tp, varnode(sym), initialize(tp));
 
         if (flags & ISDEFINED) {
                 errorp("redeclaration of '%s'", sym->name);
Received on Mon Jan 18 2016 - 17:51:56 CET

This archive was generated by hypermail 2.3.0 : Mon Jan 18 2016 - 18:00:50 CET