shithub: scc

Download patch

ref: 50dbcccb8762cbad40ebd87b42787c15d68c7c5b
parent: ed927690e4c089521410d92c9d3b06dbc33b95bd
author: Roberto E. Vargas Caballero <[email protected]>
date: Sat Mar 8 05:08:54 EST 2014

Embed the ctype into the symbol

This is the common case, so it is a good idea because it simplifies
memory management.

--- a/decl.c
+++ b/decl.c
@@ -31,7 +31,7 @@
 	} else if (yytoken == IDEN) {
 		/* we can't overflow due to the check in structdcl */
 		*symstackp++ = cursym = lookup(yytext, ns);
-		if (!cursym->ctype)
+		if (!cursym->ctype.defined)
 			cursym->ctx = curctx;
 		else if (cursym->ctx == curctx)
 			error("redeclaration of '%s'", yytext);
@@ -65,8 +65,6 @@
 	}
 }
 
-/* TODO: Add the type to the symbol */
-
 static struct symbol *
 aggregate(register struct ctype *tp)
 {
@@ -77,7 +75,8 @@
 		register struct ctype *aux;
 
 		sym = lookup(yytext, NS_TAG);
-		if (aux = sym->ctype) {
+		aux = &sym->ctype;
+		if (aux->defined) {
 			if (aux->type != tp->type) {
 				error("'%s' defined as wrong kind of tag",
 				      yytext);
@@ -84,10 +83,10 @@
 			}
 			*tp = *aux;
 		} else {
-			sym->ctype = tp;
-			tp->sym = sym;
-			tp->ns = ++nr_tags; /* FIX: It is only necessary */
-		}                           /*      in struct and union  */
+			tp->tag = sym->name;
+			tp->ns = ++nr_tags;
+			sym->ctype = *tp;
+		}
 		next();                     /* This way of handling nr_tag */
 	} else {                            /* is incorrect once is incorrect*/
 		tp->ns = ++nr_tags;         /* it will be incorrect forever*/
@@ -133,7 +132,7 @@
 				      cursym->name);
 			}
 		}
-		cursym->ctype = tp;
+		cursym->ctype = *tp;
 		cursym->qlf = qlf;
 	} while (accept(','));
 
@@ -150,7 +149,7 @@
 	if (!accept('{'))
 		return;
 
-	if (sym && !sym->ctype->forward)
+	if (sym && !sym->ctype.forward)
 		error("struct/union already defined");
 
 	if (nested_tags == NR_STRUCT_LEVEL)
@@ -157,14 +156,13 @@
 		error("too much nested structs/unions");
 
 	++nested_tags;
-	do
+	while (!accept('}'))
 		fielddcl(tp->ns);
-	while (!accept('}'));
 	--nested_tags;
 
+	if (sym)
+		sym->ctype.forward = 0;
 	tp->forward = 0;
-	if (sym = tp->sym)
-		*sym->ctype = *tp;
 }
 
 static void
@@ -183,7 +181,7 @@
 		if (yytoken != IDEN)
 			break;
 		sym = lookup(yytext, NS_IDEN);
-		sym->ctype = tp;
+		sym->ctype = *tp;
 		next();
 		if (accept('=')) {
 			expect(CONSTANT);
@@ -230,9 +228,10 @@
 				register struct symbol *sym;
 
 				sym = lookup(yytext, NS_IDEN);
-				if (sym->ctype && sym->store.c_typedef) {
+				if (sym->ctype.defined &&
+				    sym->store.c_typedef) {
 					tp = ctype(tp, TYPEDEF);
-					tp->base = sym->ctype;
+					tp->base = &sym->ctype;
 					break;
 				}
 			}
@@ -339,7 +338,8 @@
 		declarator(base, NS_IDEN);
 		cursym->store = *store;
 		cursym->qlf = *qlf;
-		tp = cursym->ctype = decl_type(base);
+		cursym->ctype = *decl_type(base);
+		tp = &cursym->ctype;
 		if ((tp->type == STRUCT || tp->type == UNION) && tp->forward)
 			error("declaration of variable with incomplete type");
 
@@ -374,7 +374,7 @@
 
 		switch (type) {
 		case STRUCT: case UNION:
-			if (!base.sym) {
+			if (!base.tag) {
 				warn(options.useless,
 				     "unnamed struct/union that defines no instances");
 			}
--- a/expr.c
+++ b/expr.c
@@ -18,7 +18,7 @@
 	switch (yytoken) {
 	case IDEN:
 		sym = lookup(yytext, NS_IDEN);
-		if (!sym->ctype)
+		if (!sym->ctype.defined)
 			error("'%s' undeclared", yytext);
 		next();
 		np = nodesym(sym);
--- a/lex.c
+++ b/lex.c
@@ -51,9 +51,9 @@
 
 	v = strtoll(s, NULL, base);
 	sym = lookup(NULL, NS_IDEN);
-	sym->ctype = tp;
+	sym->ctype = *tp;
 
-	switch (sym->ctype->type) {
+	switch (tp->type) {
 	case INT:
 		sym->i = v;
 		break;
--- a/symbol.h
+++ b/symbol.h
@@ -42,17 +42,17 @@
 	bool forward : 1;
 	bool defined: 1;
 	union {
-		unsigned len;
 		struct {
-			struct symbol *sym;
 			unsigned char ns;
+			char *tag;
 		};
+		unsigned len;
 	};
 	struct ctype *base;
 };
 
 struct symbol {
-	struct ctype *ctype;
+	struct ctype ctype;
 	struct storage store;
 	struct qualifier qlf;
 	unsigned char ctx;
--- a/types.c
+++ b/types.c
@@ -80,6 +80,7 @@
 	default:
 		assert(0);
 	}
+	tp->defined = 1;
 	return tp;
 }