shithub: scc

Download patch

ref: fe3c00a2d48a2f6d7d66231cb5edecb0c5ccf778
parent: 38facfca8aa664d42ad922e059ecfb07e1bf7ef8
author: Roberto E. Vargas Caballero <[email protected]>
date: Tue Apr 15 16:45:03 EDT 2014

Implement promote()

This function implement integer promotion, where all the
bool, char and short are transformed into integer types.

--- a/cc.h
+++ b/cc.h
@@ -9,10 +9,9 @@
 
 struct user_opt {
 	unsigned char implicit;
-	unsigned char c99;
 	unsigned char mixdcls;
+	unsigned char npromote;
 	unsigned char useless;
-	unsigned char repeat;
 	unsigned char charsign;
 };
 
@@ -113,7 +112,7 @@
 
 extern Type *typename(void);
 
-extern Type *voidtype,
+extern Type *voidtype, *booltype,
 	*uchartype,   *chartype,
 	*uinttype,    *inttype,
 	*ushortype,   *shortype,
--- a/expr.c
+++ b/expr.c
@@ -4,6 +4,7 @@
 #include "cc.h"
 
 #define SWAP(x1, x2, t) (t = x1, x1 = x2, x2 = t)
+#define GETBTYPE(n, tp, t) ((t) = (tp = UNQUAL(n->type))->op)
 
 static Symbol *zero, *one;
 
@@ -24,6 +25,16 @@
 static Node *
 promote(Node *np)
 {
+	Type *tp;
+
+	if (options.npromote)
+		return np;
+	tp = UNQUAL(np->type);
+	if (tp == chartype || tp == shortype || tp == booltype)
+		return castcode(np, inttype);
+	else if (tp == uchartype || tp == ushortype)
+		return castcode(np, uinttype);
+	return np;
 }
 
 static void
@@ -42,8 +53,10 @@
 	Type *tp1, *tp2;
 	uint8_t t1, t2;
 
-	tp1 = UNQUAL(np1->type), tp2 = UNQUAL(np2->type);
-	t1 = tp1->op, t2 = tp2->op;
+	np1 = promote(np1);
+	np2 = promote(np2);
+	GETBTYPE(np1, tp1, t1);
+	GETBTYPE(np2, tp2, t2);
 
 	if (t1 != INT || t2 != INT)
 		error("No integer operand in bit logical operation");
@@ -101,8 +114,10 @@
 	Type *tp1, *tp2, *tp3;
 	uint8_t t1, t2, taux;
 
-	tp1 = UNQUAL(np1->type), tp2 = UNQUAL(np2->type);
-	t1 = tp1->op, t2 = tp2->op;
+	np1 = promote(np1);
+	np2 = promote(np2);
+	GETBTYPE(np1, tp1, t1);
+	GETBTYPE(np2, tp2, t2);
 
 	switch (t1) {
 	case INT:
@@ -176,8 +191,10 @@
 	Type *tp1, *tp2;
 	uint8_t t1, t2;
 
-	tp1 = UNQUAL(np1->type), tp2 = UNQUAL(np2->type);
-	t1 = tp1->op, t2 = tp2->op;
+	np1 = promote(np1);
+	np2 = promote(np2);
+	GETBTYPE(np1, tp1, t1);
+	GETBTYPE(np2, tp2, t2);
 
 	switch (t1) {
 	case INT:
@@ -284,15 +301,16 @@
 incdec(Node *np, char op)
 {
 	Type *tp;
+	uint8_t t;
 	char *err;
 
+	GETBTYPE(np, tp, t);
 	if (!np->b.lvalue)
 		goto nolvalue;
-	tp = UNQUAL(np->type);
 	if (isconst(np->type->op))
 		goto const_mod;
 
-	switch (tp->op) {
+	switch (t) {
 	case PTR:
 		if (!tp->type->defined)
 			goto nocomplete;