commit 18bc293eda5e66a9cd3f86d9dcb1c987de599779
parent b82f7284d496438fd63cff37719ff25d9f9dbd61
Author: Roberto E. Vargas Caballero <k0ga@shike2.com>
Date: Mon, 5 Oct 2015 15:39:32 +0200
Add support for define() in #if
This is really stupidity of ansi c comitee, but ok, we need it.
Diffstat:
2 files changed, 36 insertions(+), 8 deletions(-)
diff --git a/cc1/cpp.c b/cc1/cpp.c
@@ -228,7 +228,9 @@ expand(char *begin, Symbol *sym)
char *arglist[NR_MACROARG], arguments[INPUTSIZ], buffer[BUFSIZE];
macroname = sym->name;
- if (!(sym->flags & ISDECLARED)) {
+ if ((sym->flags & ISDECLARED) == 0) {
+ if (namespace == NS_CPP && !strcmp(sym->name, "defined"))
+ return 0; /* we found a 'defined in an #if */
/*
* This case happens in #if were macro not defined must
* be expanded to 0
diff --git a/cc1/expr.c b/cc1/expr.c
@@ -496,6 +496,32 @@ negation(char op, Node *np)
}
}
+static Symbol *
+notdefined(Symbol *sym)
+{
+ int isdef;
+
+ if (namespace == NS_CPP && !strcmp(sym->name, "defined")) {
+ disexpand = 1;
+ next();
+ expect('(');
+ sym = yylval.sym;
+ expect(IDEN);
+ expect(')');
+
+ isdef = (sym->flags & ISDEFINED) != 0;
+ sym = newsym(NS_IDEN);
+ sym->type = inttype;
+ sym->flags |= ISCONSTANT;
+ sym->u.i = isdef;
+ disexpand = 0;
+ return sym;
+ }
+ errorp("'%s' undeclared", yytext);
+ sym->type = inttype;
+ return install(sym->ns, yylval.sym);
+}
+
/*************************************************************
* grammar functions *
*************************************************************/
@@ -505,18 +531,18 @@ primary(void)
Node *np;
Symbol *sym;
+ sym = yylval.sym;
switch (yytoken) {
case CONSTANT:
- np = constnode(yylval.sym);
+ constant:
+ np = constnode(sym);
next();
break;
case IDEN:
- sym = yylval.sym;
- if ((sym->flags & ISDECLARED) == 0) {
- errorp("'%s' undeclared", yytext);
- sym->type = inttype;
- install(sym->ns, yylval.sym);
- }
+ if ((sym->flags & ISDECLARED) == 0)
+ sym = notdefined(sym);
+ if (sym->flags & ISCONSTANT)
+ goto constant;
sym->flags |= ISUSED;
np = varnode(sym);
next();