Virgin BTL M4 as sent out in
4.1
static char sccsid
[] = "@(#)m4.c 1.3 (Berkeley) %G%";
#define HSHSIZ 199 /* prime */
#define putbak(c) *ip++ = c;
#define getchr() (ip>cur_ip?*--ip: getc(infile[infptr]))
#define putchr(c) if (cp==NULL) {if (curfile)putc(c,curfile);} else *op++ = c
DIG
, DIG
, DIG
, DIG
, DIG
, DIG
, DIG
, DIG
,
DIG
, DIG
, 0, 0, 0, 0, 0, 0,
0, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, 0, 0, 0, 0, ALPH
,
0, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
, ALPH
,
ALPH
, ALPH
, ALPH
, 0, 0, 0, 0, 0,
#define RESERVED 01 /* This is a reserved word with side action */
struct nlist
*hshtab
[HSHSIZ
];
char *ip_stk
[10] = {ibuf
};
FILE *olist
[11] = { stdout
};
FILE *curfile
= { stdout
};
FILE *infile
[10] = { stdin
};
struct call callst
[STACKS
];
int delexit(), catchsig();
makeloc
= install("MAKETEMP", eoa
, RESERVED
);
ifdefloc
= install("IFDEF", eoa
, RESERVED
);
lenloc
= install("LEN", eoa
, RESERVED
);
undefloc
= install("UNDEFINE", eoa
, RESERVED
);
shiftloc
= install("SHIFT", eoa
, RESERVED
);
cqloc
= install("CHANGEQUOTE", eoa
, RESERVED
);
defloc
= install("DEFINE", eoa
, RESERVED
);
evaloc
= install("EVAL", eoa
, RESERVED
);
inclloc
= install("INCLUDE", eoa
, RESERVED
);
sinclloc
= install("SINCLUDE", eoa
, RESERVED
);
syscmdloc
= install("SYSCMD", eoa
, RESERVED
);
dumploc
= install("DUMPDEF", eoa
, RESERVED
);
errploc
= install("ERRPRINT", eoa
, RESERVED
);
incrloc
= install("INCR", eoa
, RESERVED
);
substrloc
= install("SUBSTR", eoa
, RESERVED
);
indexloc
= install("INDEX", eoa
, RESERVED
);
transloc
= install("TRANSLIT", eoa
, RESERVED
);
ifloc
= install("IFELSE", eoa
, RESERVED
);
divloc
= install("DIVERT", eoa
, RESERVED
);
divnumloc
= install("DIVNUM", eoa
, RESERVED
);
undivloc
= install("UNDIVERT", eoa
, RESERVED
);
dnlloc
= install("DNL", eoa
, RESERVED
);
makeloc
= install("maketemp", eoa
, RESERVED
);
ifdefloc
= install("ifdef", eoa
, RESERVED
);
lenloc
= install("len", eoa
, RESERVED
);
undefloc
= install("undefine", eoa
, RESERVED
);
shiftloc
= install("shift", eoa
, RESERVED
);
cqloc
= install("changequote", eoa
, RESERVED
);
defloc
= install("define", eoa
, RESERVED
);
evaloc
= install("eval", eoa
, RESERVED
);
inclloc
= install("include", eoa
, RESERVED
);
sinclloc
= install("sinclude", eoa
, RESERVED
);
syscmdloc
= install("syscmd", eoa
, RESERVED
);
dumploc
= install("dumpdef", eoa
, RESERVED
);
errploc
= install("errprint", eoa
, RESERVED
);
incrloc
= install("incr", eoa
, RESERVED
);
substrloc
= install("substr", eoa
, RESERVED
);
indexloc
= install("index", eoa
, RESERVED
);
transloc
= install("translit", eoa
, RESERVED
);
ifloc
= install("ifelse", eoa
, RESERVED
);
divloc
= install("divert", eoa
, RESERVED
);
divnumloc
= install("divnum", eoa
, RESERVED
);
undivloc
= install("undivert", eoa
, RESERVED
);
dnlloc
= install("dnl", eoa
, RESERVED
);
if (signal(SIGHUP
, SIG_IGN
) != SIG_IGN
)
signal(SIGHUP
, catchsig
);
if (signal(SIGINT
, SIG_IGN
) != SIG_IGN
)
signal(SIGINT
, catchsig
);
tempname
= mktemp("/tmp/m4aXXXXX");
close(creat(tempname
, 0));
if (infile
[infptr
]!=stdin
)
else if ((infile
[infptr
]=fopen(argv
[0], READ
))==ERROR
) {
fprintf(stderr
, "m4: file not found: %s\n", argv
[0]);
while ((t
=type
[*tp
++=getchr()])==ALPH
||t
==DIG
);
if (*ap
= lookup(token
)->def
) {
if (++ap
>= &argstk
[STACKS
]) {
fprintf(stderr
, "m4: arg stack overflow\n");
else if (++cp
> &callst
[STACKS
]) {
fprintf(stderr
, "m4: call stack overflow\n");
/* if (t!=' ' && t!='\t') */
else /* try to fix arg count */
fprintf(stderr
, "m4: EOF in string\n");
while ((t
= getchr())!='\n'&& t
>=0)
while ( (t
=getchr())==' ' || t
=='\t' || t
=='\n')
; /* skip leading white space during arg collection */
} else if (t==' ' || t=='\t' || t=='\n') {
expand(cp
->argp
, ap
-cp
->argp
-1);
} else if (t
==COMMA
&& cp
->plev
<=1) {
while ((t
=getchr())==' ' || t
=='\t' || t
=='\n')
; /* skip leading white space during arg collection */
fprintf(stderr
, "m4: unexpected EOF\n");
fp
= fopen(tempname
, READ
);
while ((c
= getc(fp
)) > 0)
fprintf(stderr
, "m4: argument overflow\n");
fprintf(stderr
, "m4: pushback overflow\n");
for (dp
--; dp
>a1
[-1]; ) {
if (--dp
>a1
[-1] && dp
[-1]=='$') {
struct nlist
*lookup(str
)
register struct nlist
*np
;
static struct nlist nodef
;
for (np
= hshtab
[hshval
]; np
!=NULL
; np
= np
->next
) {
char *install(nam
, val
, flag
)
register struct nlist
*np
;
if ((np
= lookup(nam
))->name
== NULL
) {
np
= (struct nlist
*)malloc(sizeof(*np
));
fprintf(stderr
, "m4: no space for alloc\n");
np
->next
= hshtab
[hshval
];
register struct nlist
*np
, *tnp
;
if (c
< 1 || (np
= lookup(ap
[1]))->name
== NULL
)
tnp
= hshtab
[hshval
]; /* lookup sets hshval */
if (tnp
== np
) /* it's in first place */
hshtab
[hshval
] = np
->next
;
for ( ; tnp
->next
!= np
; tnp
= tnp
->next
)
* If this is a reserved word, it has been removed from the
* hastable. We do not want to actually free the space because
* of the code in expand. Expand wants to to pointer compairs
* to tell if this is a reserved word (e.g a special action
* needs to take place). Thus if we do not free the space,
* expand will still work, but the name will never be found
* because it out of the symbol table!
if (np
->flag
&RESERVED
== 0) { /* If not reserved free it */
p
= s1
= malloc((unsigned)strlen(s
)+1);
fprintf(stderr
, "m4: no space for alloc\n");
if (strcmp(ap
[1], ap
[2]) == 0) {
fprintf(stderr
, "m4: %s defined as itself\n", ap
[1]);
install(ap
[1], ap
[2], 0);
register struct nlist
*np
;
if (lookup(ap
[1])->name
!= NULL
)
putnum((long) strlen(ap
[1]));
lquote
= rquote
= *ap
[1];
fprintf(stderr
, "m4: shift not yet implemented\n");
register struct nlist
*np
;
if ((np
= lookup(*++ap
))->name
!= NULL
)
fprintf(stderr
, "`%s' `%s'\n", np
->name
, np
->def
);
for (np
=hshtab
[i
]; np
!=NULL
; np
=np
->next
)
fprintf(stderr
, "`%s' `%s'\n", np
->name
, np
->def
);
fprintf(stderr
, ap
[1], ap
[2], ap
[3], ap
[4], ap
[5], ap
[6]);
long evalval
; /* return value from yacc stuff */
char *pe
; /* used by grammar */
fprintf(stderr
, "m4: invalid expression in eval: %s\n", ap
[1]);
if (c
> 0 && strlen(ap
[1]) > 0) {
ip_stk
[infptr
] = cur_ip
= ip
;
if ((infile
[infptr
] = fopen(ap
[1], READ
))==ERROR
) {
fprintf(stderr
, "m4: file not found: %s\n", ap
[1]);
sign
= (num
< 0) ? '-' : '\0';
fc
= ap
[1] + max(0, min(ctoi(ap
[2]), strlen(ap
[1])));
sp
= fc
+ min(nc
, strlen(fc
));
putnum((long) strindex(ap
[1], ap
[2]));
register char *s
, *t
, *p
;
register char *s
, *fr
, *to
;
for (s
= ap
[1]; *s
; s
++) {
for (fr
= ap
[2]; *fr
; fr
++)
for (fr
= ap
[2], to
= ap
[3]; *fr
&& *to
; fr
++, to
++)
if (strcmp(ap
[1], ap
[2]) == 0) {
if (olist
[f
] || (olist
[f
]=fopen(tempname
, WRITE
))) {
if (i
==curout
|| olist
[i
]==NULL
)
fp
= fopen(tempname
, READ
);
while ((ch
= getc(fp
)) > 0)
for (j
= 1; j
<= c
; j
++) {
if (i
<1 || i
>9 || i
==curout
|| olist
[i
]==NULL
)
fp
= fopen(tempname
, READ
);
while ((ch
= getc(fp
)) > 0)
while ((t
=getchr())!='\n' && t
>=0)
while (*str
==' ' || *str
=='\t' || *str
=='\n')
while (*str
>='0' && *str
<='9')
num
= num
*10 + *str
++ - '0';