mirror of
https://github.com/openbsd/src.git
synced 2025-01-10 06:47:55 -08:00
Tracing facilities. Same style as gnu-m4, because it's mostly used for
autoconf right now.
This commit is contained in:
parent
e4ae65830a
commit
4dac505db8
@ -1,4 +1,4 @@
|
||||
# $OpenBSD: Makefile,v 1.7 2001/07/18 13:28:47 espie Exp $
|
||||
# $OpenBSD: Makefile,v 1.8 2001/09/18 14:55:52 espie Exp $
|
||||
|
||||
# -DEXTENDED
|
||||
# if you want the paste & spaste macros.
|
||||
@ -12,7 +12,7 @@ CDIAGFLAGS=-W -Wall -Wstrict-prototypes \
|
||||
CFLAGS+=-O0
|
||||
.endif
|
||||
|
||||
SRCS= eval.c expr.c look.c main.c misc.c gnum4.c
|
||||
SRCS= eval.c expr.c look.c main.c misc.c gnum4.c trace.c
|
||||
MAN= m4.1
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $OpenBSD: eval.c,v 1.34 2001/09/18 14:43:22 espie Exp $ */
|
||||
/* $OpenBSD: eval.c,v 1.35 2001/09/18 14:55:52 espie Exp $ */
|
||||
/* $NetBSD: eval.c,v 1.7 1996/11/10 21:21:29 pk Exp $ */
|
||||
|
||||
/*
|
||||
@ -41,7 +41,7 @@
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)eval.c 8.2 (Berkeley) 4/27/95";
|
||||
#else
|
||||
static char rcsid[] = "$OpenBSD: eval.c,v 1.34 2001/09/18 14:43:22 espie Exp $";
|
||||
static char rcsid[] = "$OpenBSD: eval.c,v 1.35 2001/09/18 14:55:52 espie Exp $";
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -95,14 +95,20 @@ eval(argv, argc, td)
|
||||
int argc;
|
||||
int td;
|
||||
{
|
||||
ssize_t mark = -1;
|
||||
|
||||
expansion_id++;
|
||||
if (td & RECDEF)
|
||||
errx(1, "%s at line %lu: expanding recursive definition for %s",
|
||||
CURRENT_NAME, CURRENT_LINE, argv[1]);
|
||||
if (traced_macros && is_traced(argv[1]))
|
||||
mark = trace(argv, argc, infile+ilevel);
|
||||
if (td == MACRTYPE)
|
||||
expand_macro(argv, argc);
|
||||
else
|
||||
expand_builtin(argv, argc, td);
|
||||
if (mark != -1)
|
||||
finish_trace(mark);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -634,15 +640,15 @@ dump_one_def(p)
|
||||
|
||||
if (mimic_gnu) {
|
||||
if ((p->type & TYPEMASK) == MACRTYPE)
|
||||
fprintf(stderr, "%s:\t%s\n", p->name, p->defn);
|
||||
fprintf(traceout, "%s:\t%s\n", p->name, p->defn);
|
||||
else {
|
||||
real = builtin_realname(p->type);
|
||||
if (real == NULL)
|
||||
real = null;
|
||||
fprintf(stderr, "%s:\t<%s>\n", p->name, real);
|
||||
fprintf(traceout, "%s:\t<%s>\n", p->name, real);
|
||||
}
|
||||
} else
|
||||
fprintf(stderr, "`%s'\t`%s'\n", p->name, p->defn);
|
||||
fprintf(traceout, "`%s'\t`%s'\n", p->name, p->defn);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $OpenBSD: extern.h,v 1.24 2001/09/18 14:43:22 espie Exp $ */
|
||||
/* $OpenBSD: extern.h,v 1.25 2001/09/18 14:55:52 espie Exp $ */
|
||||
/* $NetBSD: extern.h,v 1.3 1996/01/13 23:25:24 pk Exp $ */
|
||||
|
||||
/*-
|
||||
@ -95,6 +95,15 @@ extern int obtain_char __P((struct input_file *));
|
||||
extern void set_input __P((struct input_file *, FILE *, const char *));
|
||||
extern void release_input __P((struct input_file *));
|
||||
|
||||
/* trace.c */
|
||||
extern void mark_traced __P((const char *));
|
||||
extern int is_traced __P((const char *));
|
||||
extern void trace_file __P((const char *));
|
||||
extern ssize_t trace __P((const char **, int, struct input_file *));
|
||||
extern void finish_trace __P((size_t));
|
||||
extern int traced_macros;
|
||||
extern void set_trace_flags __P((const char *));
|
||||
extern FILE *traceout;
|
||||
|
||||
extern ndptr hashtab[]; /* hash table for macros etc. */
|
||||
extern stae *mstack; /* stack of m4 machine */
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $OpenBSD: main.c,v 1.45 2001/09/18 14:05:14 espie Exp $ */
|
||||
/* $OpenBSD: main.c,v 1.46 2001/09/18 14:55:52 espie Exp $ */
|
||||
/* $NetBSD: main.c,v 1.12 1997/02/08 23:54:49 cgd Exp $ */
|
||||
|
||||
/*-
|
||||
@ -47,7 +47,7 @@ static char copyright[] =
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)main.c 8.1 (Berkeley) 6/6/93";
|
||||
#else
|
||||
static char rcsid[] = "$OpenBSD: main.c,v 1.45 2001/09/18 14:05:14 espie Exp $";
|
||||
static char rcsid[] = "$OpenBSD: main.c,v 1.46 2001/09/18 14:55:52 espie Exp $";
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -192,7 +192,7 @@ main(argc,argv)
|
||||
outfile = NULL;
|
||||
resizedivs(MAXOUT);
|
||||
|
||||
while ((c = getopt(argc, argv, "gtD:U:o:I:")) != -1)
|
||||
while ((c = getopt(argc, argv, "gt:d:D:U:o:I:")) != -1)
|
||||
switch(c) {
|
||||
|
||||
case 'D': /* define something..*/
|
||||
@ -212,8 +212,11 @@ main(argc,argv)
|
||||
case 'g':
|
||||
mimic_gnu = 1;
|
||||
break;
|
||||
case 'd':
|
||||
set_trace_flags(optarg);
|
||||
break;
|
||||
case 'o':
|
||||
/* XXX accept -o for compatibility */
|
||||
trace_file(optarg);
|
||||
break;
|
||||
case '?':
|
||||
usage();
|
||||
|
222
usr.bin/m4/trace.c
Normal file
222
usr.bin/m4/trace.c
Normal file
@ -0,0 +1,222 @@
|
||||
/* $OpenBSD: trace.c,v 1.1 2001/09/18 14:55:52 espie Exp $ */
|
||||
/*
|
||||
* Copyright (c) 2001 Marc Espie.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE OPENBSD PROJECT AND CONTRIBUTORS
|
||||
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OPENBSD
|
||||
* PROJECT OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <stddef.h>
|
||||
#include <stdio.h>
|
||||
#include <err.h>
|
||||
#include "mdef.h"
|
||||
#include "stdd.h"
|
||||
#include "extern.h"
|
||||
|
||||
FILE *traceout = stderr;
|
||||
|
||||
int traced_macros = 0;
|
||||
|
||||
#define TRACE_ARGS 1
|
||||
#define TRACE_EXPANSION 2
|
||||
#define TRACE_QUOTE 4
|
||||
#define TRACE_FILENAME 8
|
||||
#define TRACE_LINENO 16
|
||||
#define TRACE_CONT 32
|
||||
#define TRACE_ID 64
|
||||
#define TRACE_NEWFILE 128 /* not implemented yet */
|
||||
#define TRACE_INPUT 256 /* not implemented yet */
|
||||
#define TRACE_ALL 512
|
||||
|
||||
|
||||
static unsigned int letter_to_flag __P((int));
|
||||
static void print_header __P((struct input_file *));
|
||||
|
||||
static unsigned int flags = TRACE_QUOTE | TRACE_EXPANSION;
|
||||
|
||||
static struct t {
|
||||
struct t *next;
|
||||
char *name;
|
||||
} *l;
|
||||
|
||||
void
|
||||
mark_traced(name)
|
||||
const char *name;
|
||||
{
|
||||
struct t *n;
|
||||
|
||||
traced_macros = 1;
|
||||
n = xalloc(sizeof(struct t));
|
||||
n->name = xstrdup(name);
|
||||
n->next = l;
|
||||
l = n;
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
is_traced(name)
|
||||
const char *name;
|
||||
{
|
||||
struct t *n;
|
||||
|
||||
if (flags & TRACE_ALL)
|
||||
return 1;
|
||||
for (n = l; n != NULL; n = n->next)
|
||||
if (STREQ(n->name, name))
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
trace_file(name)
|
||||
const char *name;
|
||||
{
|
||||
|
||||
if (traceout != stderr)
|
||||
fclose(traceout);
|
||||
traceout = fopen(name, "w");
|
||||
if (!traceout)
|
||||
err(1, "can't open %s", name);
|
||||
}
|
||||
|
||||
static unsigned int
|
||||
letter_to_flag(c)
|
||||
int c;
|
||||
{
|
||||
switch(c) {
|
||||
case 'a':
|
||||
return TRACE_ARGS;
|
||||
case 'e':
|
||||
return TRACE_EXPANSION;
|
||||
case 'q':
|
||||
return TRACE_QUOTE;
|
||||
case 'c':
|
||||
return TRACE_CONT;
|
||||
case 'x':
|
||||
return TRACE_ID;
|
||||
case 'f':
|
||||
return TRACE_FILENAME;
|
||||
case 'l':
|
||||
return TRACE_LINENO;
|
||||
case 'p':
|
||||
return TRACE_NEWFILE;
|
||||
case 'i':
|
||||
return TRACE_INPUT;
|
||||
case 't':
|
||||
return TRACE_ALL;
|
||||
case 'V':
|
||||
return ~0;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
set_trace_flags(s)
|
||||
const char *s;
|
||||
{
|
||||
char mode = 0;
|
||||
unsigned int f = 0;
|
||||
|
||||
traced_macros = 1;
|
||||
|
||||
if (*s == '+' || *s == '-')
|
||||
mode = *s++;
|
||||
while (*s)
|
||||
f |= letter_to_flag(*s++);
|
||||
switch(mode) {
|
||||
case 0:
|
||||
flags = f;
|
||||
break;
|
||||
case '+':
|
||||
flags |= f;
|
||||
break;
|
||||
case '-':
|
||||
flags &= ~f;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
print_header(inp)
|
||||
struct input_file *inp;
|
||||
{
|
||||
fprintf(traceout, "m4trace:");
|
||||
if (flags & TRACE_FILENAME)
|
||||
fprintf(traceout, "%s:", inp->name);
|
||||
if (flags & TRACE_LINENO)
|
||||
fprintf(traceout, "%lu:", inp->lineno);
|
||||
fprintf(traceout, " -1- ");
|
||||
if (flags & TRACE_ID)
|
||||
fprintf(traceout, "id %lu: ", expansion_id);
|
||||
}
|
||||
|
||||
ssize_t
|
||||
trace(argv, argc, inp)
|
||||
const char **argv;
|
||||
int argc;
|
||||
struct input_file *inp;
|
||||
{
|
||||
print_header(inp);
|
||||
if (flags & TRACE_CONT) {
|
||||
fprintf(traceout, "%s ...\n", argv[1]);
|
||||
print_header(inp);
|
||||
}
|
||||
fprintf(traceout, "%s", argv[1]);
|
||||
if ((flags & TRACE_ARGS) && argc > 2) {
|
||||
char delim = LPAREN;
|
||||
int i;
|
||||
|
||||
for (i = 2; i < argc; i++) {
|
||||
fprintf(traceout, "%c%s%s%s", delim,
|
||||
(flags & TRACE_QUOTE) ? lquote : "",
|
||||
argv[i],
|
||||
(flags & TRACE_QUOTE) ? rquote : "");
|
||||
delim = COMMA;
|
||||
}
|
||||
fprintf(traceout, "%c", RPAREN);
|
||||
}
|
||||
if (flags & TRACE_CONT) {
|
||||
fprintf(traceout, " -> ???\n");
|
||||
print_header(inp);
|
||||
fprintf(traceout, argc > 2 ? "%s(...)" : "%s", argv[1]);
|
||||
}
|
||||
if (flags & TRACE_EXPANSION)
|
||||
return buffer_mark();
|
||||
else {
|
||||
fprintf(traceout, "\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
finish_trace(mark)
|
||||
size_t mark;
|
||||
{
|
||||
fprintf(traceout, " -> ");
|
||||
if (flags & TRACE_QUOTE)
|
||||
fprintf(traceout, "%s", lquote);
|
||||
dump_buffer(traceout, mark);
|
||||
if (flags & TRACE_QUOTE)
|
||||
fprintf(traceout, "%s", rquote);
|
||||
fprintf(traceout, "\n");
|
||||
}
|
Loading…
Reference in New Issue
Block a user