summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorragge <ragge>2008-08-15 15:29:27 +0000
committerragge <ragge>2008-08-15 15:29:27 +0000
commitd430c9dd10dae93fd9d0cb4d25596c2b7f173c93 (patch)
treecbd604a954e1a6aba3d5ac9546b573eb2bfac35a
parent3d068f74c9b84b36f74d22581bcd49830454325d (diff)
Understand the ##arg syntax for gnu cpp.
-rw-r--r--cpp.c29
1 files changed, 28 insertions, 1 deletions
diff --git a/cpp.c b/cpp.c
index aab6391..7ec242f 100644
--- a/cpp.c
+++ b/cpp.c
@@ -152,6 +152,7 @@ usch *stringbuf = sbf;
* 1-> - number of args.
*/
+#define GCCARG 0xfd /* has gcc varargs that may be replaced with 0 */
#define VARG 0xfe /* has varargs */
#define OBJCT 0xff
#define WARN 1 /* SOH, not legal char */
@@ -627,6 +628,7 @@ define()
int ellips = 0;
#ifdef GCC_VARI
usch *gccvari = NULL;
+ int wascon;
#endif
if (flslvl)
@@ -698,6 +700,10 @@ define()
/* parse replacement-list, substituting arguments */
savch('\0');
while (c != '\n') {
+#ifdef GCC_VARI
+ wascon = 0;
+loop:
+#endif
switch (c) {
case WSPACE:
/* remove spaces if it surrounds a ## directive */
@@ -709,6 +715,12 @@ define()
savch(CONC);
if ((c = yylex()) == WSPACE)
c = yylex();
+#ifdef GCC_VARI
+ if (c == '\n')
+ break;
+ wascon = 1;
+ goto loop;
+#endif
}
continue;
@@ -717,7 +729,14 @@ define()
savch(CONC);
if ((c = yylex()) == WSPACE)
c = yylex();
+#ifdef GCC_VARI
+ if (c == '\n')
+ break;
+ wascon = 1;
+ goto loop;
+#else
continue;
+#endif
case MKSTR:
if (narg < 0) {
@@ -745,7 +764,7 @@ define()
#ifdef GCC_VARI
if (gccvari &&
strcmp(yytext, (char *)gccvari) == 0) {
- savch(VARG);
+ savch(wascon ? GCCARG : VARG);
savch(WARN);
if (mkstr)
savch(SNUFF), mkstr = 0;
@@ -1325,6 +1344,14 @@ expdef(vp, rp, gotwarn)
if (sp[-1] == VARG) {
bp = ap = args[narg];
sp--;
+#ifdef GCC_VARI
+ } else if (sp[-1] == GCCARG) {
+ ap = args[narg];
+ if (ap[0] == 0)
+ ap = (usch *)"0";
+ bp = ap;
+ sp--;
+#endif
} else
bp = ap = args[(int)*--sp];
if (sp[2] != CONC && !snuff && sp[-1] != CONC) {