On 2009/10/14 08:38, Matthew Dempsky wrote:
>
> Doesn't this leak memory in the -P case? What about moving the
> xstrdup() call into only the !prefix_builtins path? Then you can also
> eliminate the const cast:
Yes, Tobias Ulmer noticed this too, I didn't think of a way around
it before but this makes a lot more sense - thanks.
New diff incorporates your fix and jmc's feedback, and adds a
simple regression test. (The existing tests still pass).
Index: usr.bin/m4/extern.h
===================================================================
RCS file: /cvs/src/usr.bin/m4/extern.h,v
retrieving revision 1.48
diff -u -p -r1.48 extern.h
--- usr.bin/m4/extern.h 21 Aug 2008 20:59:14 -0000 1.48
+++ usr.bin/m4/extern.h 14 Oct 2009 16:31:36 -0000
@@ -173,4 +173,5 @@ extern char scommt[MAXCCHARS+1];/* start
extern int synch_lines; /* line synchronisation directives */
extern int mimic_gnu; /* behaves like gnu-m4 */
+extern int prefix_builtins; /* prefix builtin macros with m4_ */
Index: usr.bin/m4/look.c
===================================================================
RCS file: /cvs/src/usr.bin/m4/look.c,v
retrieving revision 1.19
diff -u -p -r1.19 look.c
--- usr.bin/m4/look.c 26 Jun 2009 22:03:17 -0000 1.19
+++ usr.bin/m4/look.c 14 Oct 2009 16:31:36 -0000
@@ -231,11 +231,19 @@ void
setup_builtin(const char *name, unsigned int type)
{
ndptr n;
+ char *name2;
- n = create_entry(name);
+ if(prefix_builtins) {
+ name2 = xalloc(strlen(name)+3+1, NULL);
+ memcpy(name2, "m4_", 3);
+ memcpy(name2 + 3, name, strlen(name)+1);
+ } else
+ name2 = xstrdup(name);
+
+ n = create_entry(name2);
n->builtin_type = type;
n->d = xalloc(sizeof(struct macro_definition), NULL);
- n->d->defn = xstrdup(name);
+ n->d->defn = name2;
n->d->type = type;
n->d->next = NULL;
}
Index: usr.bin/m4/m4.1
===================================================================
RCS file: /cvs/src/usr.bin/m4/m4.1,v
retrieving revision 1.55
diff -u -p -r1.55 m4.1
--- usr.bin/m4/m4.1 8 Feb 2009 17:15:10 -0000 1.55
+++ usr.bin/m4/m4.1 14 Oct 2009 16:31:36 -0000
@@ -38,7 +38,7 @@
.Nd macro language processor
.Sh SYNOPSIS
.Nm m4
-.Op Fl gs
+.Op Fl gPs
.Oo
.Sm off
.Fl D Ar name Op No = Ar value
@@ -150,6 +150,13 @@ to the include path.
.It Fl o Ar filename
Send trace output to
.Ar filename .
+.It Fl P
+Prefix all built-in macros with
+.Sq m4_ .
+For example, instead of writing
+.Ic define ,
+use
+.Ic m4_define .
.It Fl s
Output line synchronization directives, suitable for
.Xr cpp 1 .
Index: usr.bin/m4/main.c
===================================================================
RCS file: /cvs/src/usr.bin/m4/main.c,v
retrieving revision 1.76
diff -u -p -r1.76 main.c
--- usr.bin/m4/main.c 16 Aug 2008 12:21:46 -0000 1.76
+++ usr.bin/m4/main.c 14 Oct 2009 16:31:36 -0000
@@ -77,6 +77,7 @@ char rquote[MAXCCHARS+1] = {RQUOTE}; /*
char scommt[MAXCCHARS+1] = {SCOMMT}; /* start character for comment */
char ecommt[MAXCCHARS+1] = {ECOMMT}; /* end character for comment */
int synch_lines = 0; /* line synchronisation for C preprocessor */
+int prefix_builtins = 0; /* -P option to prefix builtin keywords */
struct keyblk {
char *knam; /* keyword name */
@@ -175,7 +176,6 @@ main(int argc, char *argv[])
signal(SIGINT, onintr);
init_macros();
- initkwds();
initspaces();
STACKMAX = INITSTACKMAX;
@@ -186,7 +186,7 @@ main(int argc, char *argv[])
outfile = NULL;
resizedivs(MAXOUT);
- while ((c = getopt(argc, argv, "gst:d:D:U:o:I:")) != -1)
+ while ((c = getopt(argc, argv, "gst:d:D:U:o:I:P")) != -1)
switch(c) {
case 'D': /* define something..*/
@@ -200,12 +200,14 @@ main(int argc, char *argv[])
case 'I':
addtoincludepath(optarg);
break;
+ case 'P':
+ prefix_builtins = 1;
+ break;
case 'U': /* undefine... */
macro_popdef(optarg);
break;
case 'g':
mimic_gnu = 1;
- setup_builtin("format", FORMATTYPE);
break;
case 'd':
set_trace_flags(optarg);
@@ -225,6 +227,10 @@ main(int argc, char *argv[])
argc -= optind;
argv += optind;
+
+ initkwds();
+ if (mimic_gnu)
+ setup_builtin("format", FORMATTYPE);
active = stdout; /* default active output */
bbase[0] = bufbase;
Index: usr.bin/m4/misc.c
===================================================================
RCS file: /cvs/src/usr.bin/m4/misc.c,v
retrieving revision 1.40
diff -u -p -r1.40 misc.c
--- usr.bin/m4/misc.c 21 Aug 2008 20:59:14 -0000 1.40
+++ usr.bin/m4/misc.c 14 Oct 2009 16:31:36 -0000
@@ -341,7 +341,7 @@ xstrdup(const char *s)
void
usage()
{
- fprintf(stderr, "usage: m4 [-gs] [-Dname[=value]] [-d flags] "
+ fprintf(stderr, "usage: m4 [-gPs] [-Dname[=value]] [-d flags] "
"[-I dirname] [-o filename]\n"
"\t[-t macro] [-Uname] [file ...]\n");
exit(1);
Index: regress/usr.bin/m4/Makefile
===================================================================
RCS file: /cvs/src/regress/usr.bin/m4/Makefile,v
retrieving revision 1.25
diff -u -p -r1.25 Makefile
--- regress/usr.bin/m4/Makefile 16 Aug 2008 10:02:32 -0000 1.25
+++ regress/usr.bin/m4/Makefile 14 Oct 2009 16:31:35 -0000
@@ -11,7 +11,7 @@ REGRESS_TARGETS= test-ff_after_dnl test-
test-patterns trip test-strangequotes test-redef test-quotes \
test-weird test-args test-args2 test-esyscmd test-eval test-gnupatterns \
test-gnupatterns2 test-comments test-synch1 test-synch1bis \
- test-gnuformat test-includes
+ test-gnuformat test-includes test-gnuprefix
test-ff_after_dnl: ff_after_dnl.m4
${M4} ff_after_dnl.m4 | diff - ${.CURDIR}/ff_after_dnl.out
@@ -91,6 +91,10 @@ test-synch1:
test-synch1bis:
${M4} -s <${.CURDIR}/synch1.m4|perl ${.CURDIR}/reconstitute|\
grep MARK| diff - ${.CURDIR}/synch1bis.out
+
+test-gnuprefix:
+ ${M4} -P ${.CURDIR}/gnuprefix.m4 2>&1 | \
+ diff -u - ${.CURDIR}/gnuprefix.out
.PHONY: ${REGRESS_TARGETS}
Index: regress/usr.bin/m4/gnuprefix.m4
===================================================================
RCS file: regress/usr.bin/m4/gnuprefix.m4
diff -N regress/usr.bin/m4/gnuprefix.m4
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ regress/usr.bin/m4/gnuprefix.m4 14 Oct 2009 16:31:35 -0000
@@ -0,0 +1,2 @@
+dumpdef()
+m4_dumpdef()
Index: regress/usr.bin/m4/gnuprefix.out
===================================================================
RCS file: regress/usr.bin/m4/gnuprefix.out
diff -N regress/usr.bin/m4/gnuprefix.out
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ regress/usr.bin/m4/gnuprefix.out 14 Oct 2009 16:31:35 -0000
@@ -0,0 +1,45 @@
+`m4_ifelse' `m4_ifelse'
+`m4_dnl' `m4_dnl'
+`m4_expr' `m4_expr'
+`m4_builtin' `m4_builtin'
+`m4_popdef' `m4_popdef'
+`m4_eval' `m4_eval'
+`m4_len' `m4_len'
+`m4_indir' `m4_indir'
+`m4_sinclude' `m4_sinclude'
+`m4_index' `m4_index'
+`m4_traceoff' `m4_traceoff'
+`m4___file__' `m4___file__'
+`m4_unix' `m4_unix'
+`m4_changecom' `m4_changecom'
+`m4_defn' `m4_defn'
+`m4_decr' `m4_decr'
+`m4_translit' `m4_translit'
+`m4_patsubst' `m4_patsubst'
+`m4_dumpdef' `m4_dumpdef'
+`m4___line__' `m4___line__'
+`m4_esyscmd' `m4_esyscmd'
+`m4_traceon' `m4_traceon'
+`m4_incr' `m4_incr'
+`m4_shift' `m4_shift'
+`m4_syscmd' `m4_syscmd'
+`m4_include' `m4_include'
+`m4_pushdef' `m4_pushdef'
+`m4_paste' `m4_paste'
+`m4_regexp' `m4_regexp'
+`m4_changequote' `m4_changequote'
+`m4_undivert' `m4_undivert'
+`m4_m4exit' `m4_m4exit'
+`m4_substr' `m4_substr'
+`m4_m4wrap' `m4_m4wrap'
+`m4_ifdef' `m4_ifdef'
+`m4_sysval' `m4_sysval'
+`m4_divert' `m4_divert'
+`m4_maketemp' `m4_maketemp'
+`m4_spaste' `m4_spaste'
+`m4_define' `m4_define'
+`m4_undefine' `m4_undefine'
+`m4_divnum' `m4_divnum'
+`m4_errprint' `m4_errprint'
+dumpdef()
+