"#macro test\nnested macro $1\n#macro "
"nested\ncontent $1\n#endmacro\nafter\nnested n1\n#endmacro\ntest t1");
- assert_preproc("test defined!\n", 0,
- "#define test\n#ifdef test\ntest defined!\n#endif");
+ // ifdef
+ assert_preproc(
+ "before\nifdeftest defined!\nafter", 0,
+ "before\n#define test\n#ifdef test\nifdeftest defined!\n#endif\nafter");
+ assert_preproc("before\nafter", 0,
+ "before\n#ifdef test\nifdeftest defined!\n#endif\nafter");
+ assert_preproc("ifdeftest defined!\n", -1,
+ "#define test\n#ifdef test\nifdeftest defined!\n");
+
+ // ifndef
+ assert_preproc("before\nifndeftest defined!\nafter", 0,
+ "before\n#ifndef test\nifndeftest defined!\n#endif\nafter");
+ assert_preproc(
+ "before\nafter", 0,
+ "before\n#define test\n#ifndef test\nifndeftest defined!\n#endif\nafter");
+ assert_preproc("ifndeftest defined!\n", -1,
+ "#ifndef test\nifndeftest defined!\n");
TESTEND("preproc");
}
int ulas_preprocline(struct ulas_preproc *pp, FILE *dst, FILE *src,
const char *raw_line, size_t n) {
+ /**
+ * We do use raw pointers to the line here... which is fine
+ * as long as it is never used after a recursive call to the preprocessor!
+ * never use this pointer after such a recursive call!
+ */
char *line = ulas_preprocexpand(pp, raw_line, &n);
const char *pline = line;
if (found_dir != ULAS_PPDIR_NONE) {
ulas_trimend('\n', line, strlen(line));
-
switch (found_dir) {
case ULAS_PPDIR_DEF: {
// next token is a name
ULASERR("Expected name for #if(n)def\n");
return -1;
}
+ struct ulas_ppdef *def =
+ ulas_preprocgetdef(pp, pp->tok.buf, pp->tok.maxlen);
// the end of a directive should have no further tokens!
if (ulas_preprochasstray(pp, pline, n)) {
char buf[ULAS_LINEMAX];
memset(buf, 0, ULAS_LINEMAX);
- FILE *defdst = dst;
+ FILE *defdst = NULL;
+ if ((def && found_dir == ULAS_PPDIR_IFDEF) ||
+ (!def && found_dir == ULAS_PPDIR_IFNDEF)) {
+ defdst = dst;
+ }
// loop until end of line or endif
int rc = 0;
while ((rc = ulas_preprocnext(pp, defdst, src, buf, ULAS_LINEMAX)) > 0) {
if (rc == ULAS_PPDIR_ENDIF) {
// we need to clear the line buffer to now echo back
- // the #endmacro directive
+ // the #endif directive
pp->line.buf[0] = '\0';
break;
}