shithub: scc

Download patch

ref: f6d8f8f304878b3c0e4544d055b29482f818f13e
parent: 9b1eafb87ca51b32030a2a53bed3f2170bf2f936
author: Roberto E. Vargas Caballero <k0ga@shike2.com>
date: Thu Aug 13 12:21:01 EDT 2015

Fix #if with not defined macros

When a not defined macro appears in a #if then it must be evaluated
to 0.

--- a/cc1/cpp.c
+++ b/cc1/cpp.c
@@ -195,6 +195,16 @@
 	char *arglist[NR_MACROARG], arguments[INPUTSIZ], buffer[BUFSIZE];
 
 	macroname = sym->name;
+	if (!(sym->flags & ISDECLARED)) {
+		/*
+		 * This case happens in #if were macro not defined must
+		 * be expanded to 0
+		 */
+		buffer[0] = '0';
+		buffer[1] = '\0';
+		elen = 1;
+		goto substitute;
+	}
 	if (sym == symfile) {
 		elen = sprintf(buffer, "\"%s\" ", input->fname);
 		goto substitute;
@@ -231,6 +241,9 @@
 
 	input->p = input->begin = begin;
 
+	if (!(sym->flags & ISDECLARED))
+		delmacro(sym);
+
 	return 1;
 }
 #undef BUFSIZE
@@ -327,6 +340,7 @@
 		sym->flags |= ISDECLARED;
 	}
 
+	setnamespace(NS_IDEN);       /* Avoid polution in NS_CPP */
 	next();
 	if ((n = getpars(args)) == NR_MACROARG)
 		goto delete;
@@ -502,6 +516,7 @@
 cppif(void)
 {
 	setnamespace(NS_CPP);
+	disexpand = 0;
 	next();
 	ifclause(0, 0);
 }
@@ -548,6 +563,8 @@
 static void
 elif(void)
 {
+	setnamespace(NS_CPP);
+	disexpand = 0;
 	elseclause();
 	ifclause(0, 0);
 }
--- a/cc1/lex.c
+++ b/cc1/lex.c
@@ -18,7 +18,7 @@
 int cppoff;
 int lexmode = CCMODE;
 
-static unsigned lex_ns = NS_IDEN;
+static unsigned lex_ns = NS_IDEN, saved_ns;
 static int safe, eof;
 Input *input;
 
@@ -380,7 +380,7 @@
 	input->p = p;
 	tok2str();
 	sym = lookup(lex_ns);
-	if (sym->ns == NS_CPP && lexmode == CCMODE) {
+	if (sym->ns == NS_CPP) {
 		if (!disexpand && expand(begin, sym))
 			return next();
 		/*
@@ -493,6 +493,7 @@
 void
 setnamespace(int ns)
 {
+	saved_ns = (ns == NS_CPPCLAUSES) ? lex_ns : 0;
 	lex_ns = ns;
 }
 
@@ -518,6 +519,8 @@
 	skipspaces();
 	c = *input->begin;
 	if ((eof || lexmode == CPPMODE) && c == '\0') {
+		if (lexmode == CPPMODE)
+			lex_ns = saved_ns;
 		strcpy(yytext, "<EOF>");
 		if (cppctx && eof)
 			error("#endif expected");
@@ -538,7 +541,8 @@
 
 exit:
 	DBG(stderr, "TOKEN %s\n", yytext);
-	lex_ns = NS_IDEN;
+	if (lexmode == CCMODE)
+		lex_ns = NS_IDEN;
 	return yytoken;
 }