commit - 121058d7e6994e3577bbe541317d23db95847ace
commit + 14c31a433b611c8184d7d503eb71a5e7c648ef09
blob - cc565367073134d2ca3c57c3490c0c75658581ce
blob + 23136af5fef103ce02a1dc2506d9f42292b3bdf3
--- template/parse.y
+++ template/parse.y
int lineno;
int errors;
} *file, *topfile;
-int parse(const char *);
+int parse(FILE *, const char *);
struct file *pushfile(const char *, int);
int popfile(void);
int yyparse(void);
extern int nodebug;
+static FILE *fp;
+
static int block;
static int in_define;
static int errors;
| verbatim1 STRING {
if (*$2 != '\0') {
dbg();
- puts($2);
+ fprintf(fp, "%s\n", $2);
}
free($2);
}
raw : STRING {
dbg();
- printf("if ((tp_ret = tp->tp_puts(tp, ");
+ fprintf(fp, "if ((tp_ret = tp->tp_puts(tp, ");
printq($1);
- puts(")) == -1) goto err;");
+ fputs(")) == -1) goto err;\n", fp);
free($1);
}
;
block : define body end {
- puts("err:");
- puts("return tp_ret;");
- puts("}");
+ fputs("err:\n", fp);
+ fputs("return tp_ret;\n", fp);
+ fputs("}\n", fp);
in_define = 0;
}
| define body finally end {
- puts("return tp_ret;");
- puts("}");
+ fputs("return tp_ret;\n", fp);
+ fputs("}\n", fp);
in_define = 0;
}
;
in_define = 1;
dbg();
- printf("int\n%s\n{\n", $3);
- puts("int tp_ret = 0;");
+ fprintf(fp, "int\n%s\n{\n", $3);
+ fputs("int tp_ret = 0;\n", fp);
free($3);
}
special : '{' RENDER string '}' {
dbg();
- printf("if ((tp_ret = %s) == -1) goto err;\n", $3);
+ fprintf(fp, "if ((tp_ret = %s) == -1) goto err;\n",
+ $3);
free($3);
}
| printf
- | if body endif { puts("}"); }
+ | if body endif { fputs("}\n", fp); }
| loop
| '{' string '|' UNSAFE '}' {
dbg();
- printf("if ((tp_ret = tp->tp_puts(tp, %s)) == -1)\n",
+ fprintf(fp,
+ "if ((tp_ret = tp->tp_puts(tp, %s)) == -1)\n",
$2);
- puts("goto err;");
+ fputs("goto err;\n", fp);
free($2);
}
| '{' string '|' URLESCAPE '}' {
dbg();
- printf("if ((tp_ret = tp_urlescape(tp, %s)) == -1)\n",
+ fprintf(fp,
+ "if ((tp_ret = tp_urlescape(tp, %s)) == -1)\n",
$2);
- puts("goto err;");
+ fputs("goto err;\n", fp);
free($2);
}
| '{' string '}' {
dbg();
- printf("if ((tp_ret = tp->tp_escape(tp, %s)) == -1)\n",
+ fprintf(fp,
+ "if ((tp_ret = tp->tp_escape(tp, %s)) == -1)\n",
$2);
- puts("goto err;");
+ fputs("goto err;\n", fp);
free($2);
}
;
printf : '{' PRINTF {
dbg();
- printf("if (asprintf(&tp->tp_tmp, ");
+ fprintf(fp, "if (asprintf(&tp->tp_tmp, ");
} printfargs '}' {
- puts(") == -1)");
- puts("goto err;");
- puts("if ((tp_ret = tp->tp_escape(tp, tp->tp_tmp)) "
- "== -1)");
- puts("goto err;");
- puts("free(tp->tp_tmp);");
- puts("tp->tp_tmp = NULL;");
+ fputs(") == -1)\n", fp);
+ fputs("goto err;\n", fp);
+ fputs("if ((tp_ret = tp->tp_escape(tp, tp->tp_tmp)) "
+ "== -1)\n", fp);
+ fputs("goto err;\n", fp);
+ fputs("free(tp->tp_tmp);\n", fp);
+ fputs("tp->tp_tmp = NULL;\n", fp);
}
;
printfargs : /* empty */
| printfargs STRING {
- printf(" %s", $2);
+ fprintf(fp, " %s", $2);
free($2);
}
;
if : '{' IF stringy '}' {
dbg();
- printf("if (%s) {\n", $3);
+ fprintf(fp, "if (%s) {\n", $3);
free($3);
}
;
elsif : '{' ELSE IF stringy '}' {
dbg();
- printf("} else if (%s) {\n", $4);
+ fprintf(fp, "} else if (%s) {\n", $4);
free($4);
}
;
else : '{' ELSE '}' {
dbg();
- puts("} else {");
+ fputs("} else {\n", fp);
}
;
loop : '{' FOR stringy '}' {
- printf("for (%s) {\n", $3);
+ fprintf(fp, "for (%s) {\n", $3);
free($3);
} body end {
- puts("}");
+ fputs("}\n", fp);
}
| '{' TQFOREACH STRING STRING STRING '}' {
- printf("TAILQ_FOREACH(%s, %s, %s) {\n",
+ fprintf(fp, "TAILQ_FOREACH(%s, %s, %s) {\n",
$3, $4, $5);
free($3);
free($4);
free($5);
} body end {
- puts("}");
+ fputs("}\n", fp);
}
;
finally : '{' FINALLY '}' {
dbg();
- puts("err:");
+ fputs("err:\n", fp);
} verbatims
;
}
int
-parse(const char *filename)
+parse(FILE *outfile, const char *filename)
{
+ fp = outfile;
+
if ((file = pushfile(filename, 0)) == 0)
return (-1);
topfile = file;
}
lastline = yylval.lineno;
- printf("#line %d ", yylval.lineno);
+ fprintf(fp, "#line %d ", yylval.lineno);
printq(file->name);
- putchar('\n');
+ putc('\n', fp);
}
void
printq(const char *str)
{
- putchar('"');
+ putc('"', fp);
for (; *str; ++str) {
if (*str == '"')
- putchar('\\');
- putchar(*str);
+ putc('\\', fp);
+ putc(*str, fp);
}
- putchar('"');
+ putc('"', fp);
}
blob - f35c12a5a774cca9c6314d3441274f74714d17a9
blob + 9049862265fd87ccc1ab78e1c8e5be7694633be0
--- template/template.c
+++ template/template.c
#include <stdlib.h>
#include <unistd.h>
-int parse(const char *);
+int parse(FILE *, const char *);
-int nodebug;
+int nodebug;
static void __dead
usage(void)
int
main(int argc, char **argv)
{
- int ch, i;
+ FILE *fp = stdout;
+ const char *out = NULL;
+ int ch, i;
- if (pledge("stdio rpath", NULL) == -1)
- err(1, "pledge");
-
- while ((ch = getopt(argc, argv, "G")) != -1) {
+ while ((ch = getopt(argc, argv, "Go:")) != -1) {
switch (ch) {
case 'G':
nodebug = 1;
break;
+ case 'o':
+ out = optarg;
+ break;
default:
usage();
}
argc -= optind;
argv += optind;
+ if (out && (fp = fopen(out, "w")) == NULL)
+ err(1, "can't open %s", out);
+
+ if (out && unveil(out, "wc") == -1)
+ err(1, "unveil %s", out);
+ if (unveil("/", "r") == -1)
+ err(1, "unveil /");
+ if (pledge(out ? "stdio rpath cpath" : "stdio rpath", NULL) == -1)
+ err(1, "pledge");
+
/* preamble */
- puts("#include \"tmpl.h\"");
+ fprintf(fp, "#include \"tmpl.h\"\n");
if (argc == 0) {
- parse("/dev/stdin");
- exit(0);
+ if (parse(fp, "/dev/stdin") == -1)
+ goto err;
+ } else {
+ for (i = 0; i < argc; ++i)
+ if (parse(fp, argv[i]) == -1)
+ goto err;
}
- for (i = 0; i < argc; ++i)
- if (parse(argv[i]) == -1)
- return (1);
+ if (ferror(fp))
+ goto err;
+ if (fclose(fp) == -1) {
+ fp = NULL;
+ goto err;
+ }
+
return (0);
+
+err:
+ if (fp)
+ fclose(fp);
+ if (out && unlink(out) == -1)
+ err(1, "unlink %s", out);
+ return (1);
}