1/*-
2 * Copyright (c) 1988, 1989, 1990, 1993
3 *	The Regents of the University of California.  All rights reserved.
4 * Copyright (c) 1989 by Berkeley Softworks
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to Berkeley by
8 * Adam de Boor.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 * 3. All advertising materials mentioning features or use of this software
19 *    must display the following acknowledgement:
20 *	This product includes software developed by the University of
21 *	California, Berkeley and its contributors.
22 * 4. Neither the name of the University nor the names of its contributors
23 *    may be used to endorse or promote products derived from this software
24 *    without specific prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
27 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
30 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 * SUCH DAMAGE.
37 *
38 * @(#)parse.c	8.3 (Berkeley) 3/19/94
39 */
40
41#include <sys/cdefs.h>
42__FBSDID("$FreeBSD$");
43
44/*-
45 * parse.c --
46 *	Functions to parse a makefile.
47 *
48 *	Most important structures are kept in Lsts. Directories for
49 *	the #include "..." function are kept in the 'parseIncPath' Lst, while
50 *	those for the #include <...> are kept in the 'sysIncPath' Lst. The
51 *	targets currently being defined are kept in the 'targets' Lst.
52 *
53 * Interface:
54 *
55 *	Parse_File	Function used to parse a makefile. It must
56 *			be given the name of the file, which should
57 *			already have been opened, and a function
58 *			to call to read a character from the file.
59 *
60 *	Parse_IsVar	Returns TRUE if the given line is a
61 *			variable assignment. Used by MainParseArgs
62 *			to determine if an argument is a target
63 *			or a variable assignment. Used internally
64 *			for pretty much the same thing...
65 *
66 *	Parse_Error	Function called when an error occurs in
67 *			parsing. Used by the variable and
68 *			conditional modules.
69 *
70 *	Parse_MainName	Returns a Lst of the main target to create.
71 */
72
73#include <assert.h>
74#include <ctype.h>
75#include <stdarg.h>
76#include <string.h>
77#include <stdlib.h>
78#include <err.h>
79
80#include "arch.h"
81#include "buf.h"
82#include "cond.h"
83#include "config.h"
84#include "dir.h"
85#include "for.h"
86#include "globals.h"
87#include "GNode.h"
88#include "hash_tables.h"
89#include "job.h"
90#include "make.h"
91#include "parse.h"
92#include "pathnames.h"
93#include "shell.h"
94#include "str.h"
95#include "suff.h"
96#include "targ.h"
97#include "util.h"
98#include "var.h"
99
100/*
101 * These values are returned by ParsePopInput to tell Parse_File whether to
102 * CONTINUE parsing, i.e. it had only reached the end of an include file,
103 * or if it's DONE.
104 */
105#define	CONTINUE	1
106#define	DONE		0
107
108/* targets we're working on */
109static Lst targets = Lst_Initializer(targets);
110
111/* true if currently in a dependency line or its commands */
112static Boolean inLine;
113
114static int fatals = 0;
115
116/*
117 * The main target to create. This is the first target on the
118 * first dependency line in the first makefile.
119 */
120static GNode *mainNode;
121
122/*
123 * Definitions for handling #include specifications
124 */
125struct IFile {
126	char	*fname;		/* name of previous file */
127	int	lineno;		/* saved line number */
128	FILE	*F;		/* the open stream */
129	char	*str;		/* the string when parsing a string */
130	char	*ptr;		/* the current pointer when parsing a string */
131	TAILQ_ENTRY(IFile) link;/* stack the files */
132};
133
134/* stack of IFiles generated by * #includes */
135static TAILQ_HEAD(, IFile) includes = TAILQ_HEAD_INITIALIZER(includes);
136
137/* access current file */
138#define	CURFILE	(TAILQ_FIRST(&includes))
139
140/* list of directories for "..." includes */
141struct Path parseIncPath = TAILQ_HEAD_INITIALIZER(parseIncPath);
142
143/* list of directories for <...> includes */
144struct Path sysIncPath = TAILQ_HEAD_INITIALIZER(sysIncPath);
145
146/*
147 * specType contains the SPECial TYPE of the current target. It is
148 * Not if the target is unspecial. If it *is* special, however, the children
149 * are linked as children of the parent but not vice versa. This variable is
150 * set in ParseDoDependency
151 */
152typedef enum {
153	Begin,		/* .BEGIN */
154	Default,	/* .DEFAULT */
155	End,		/* .END */
156	ExportVar,	/* .EXPORTVAR */
157	Ignore,		/* .IGNORE */
158	Includes,	/* .INCLUDES */
159	Interrupt,	/* .INTERRUPT */
160	Libs,		/* .LIBS */
161	MFlags,		/* .MFLAGS or .MAKEFLAGS */
162	Main,		/* .MAIN and we don't have anyth. user-spec. to make */
163	Not,		/* Not special */
164	NotParallel,	/* .NOTPARALELL */
165	Null,		/* .NULL */
166	Order,		/* .ORDER */
167	Parallel,	/* .PARALLEL */
168	ExPath,		/* .PATH */
169	Phony,		/* .PHONY */
170	Posix,		/* .POSIX */
171	MakefileDeps,	/* .MAKEFILEDEPS */
172	Precious,	/* .PRECIOUS */
173	ExShell,	/* .SHELL */
174	Silent,		/* .SILENT */
175	SingleShell,	/* .SINGLESHELL */
176	Suffixes,	/* .SUFFIXES */
177	Wait,		/* .WAIT */
178	Warn,		/* .WARN */
179	Attribute	/* Generic attribute */
180} ParseSpecial;
181
182static ParseSpecial specType;
183static int waiting;
184
185/*
186 * Predecessor node for handling .ORDER. Initialized to NULL when .ORDER
187 * seen, then set to each successive source on the line.
188 */
189static GNode *predecessor;
190
191/*
192 * The parseKeywords table is searched using binary search when deciding
193 * if a target or source is special. The 'spec' field is the ParseSpecial
194 * type of the keyword ("Not" if the keyword isn't special as a target) while
195 * the 'op' field is the operator to apply to the list of targets if the
196 * keyword is used as a source ("0" if the keyword isn't special as a source)
197 */
198static const struct keyword {
199	const char	*name;	/* Name of keyword */
200	ParseSpecial	spec;	/* Type when used as a target */
201	int		op;	/* Operator when used as a source */
202} parseKeywords[] = {
203	/* KEYWORD-START-TAG */
204	{ ".BEGIN",		Begin,		0 },
205	{ ".DEFAULT",		Default,	0 },
206	{ ".END",		End,		0 },
207	{ ".EXEC",		Attribute,	OP_EXEC },
208	{ ".EXPORTVAR",		ExportVar,	0 },
209	{ ".IGNORE",		Ignore,		OP_IGNORE },
210	{ ".INCLUDES",		Includes,	0 },
211	{ ".INTERRUPT",		Interrupt,	0 },
212	{ ".INVISIBLE",		Attribute,	OP_INVISIBLE },
213	{ ".JOIN",		Attribute,	OP_JOIN },
214	{ ".LIBS",		Libs,		0 },
215	{ ".MAIN",		Main,		0 },
216	{ ".MAKE",		Attribute,	OP_MAKE },
217	{ ".MAKEFILEDEPS",	MakefileDeps,	0 },
218	{ ".MAKEFLAGS",		MFlags,		0 },
219	{ ".MFLAGS",		MFlags,		0 },
220	{ ".NOTMAIN",		Attribute,	OP_NOTMAIN },
221	{ ".NOTPARALLEL",	NotParallel,	0 },
222	{ ".NO_PARALLEL",	NotParallel,	0 },
223	{ ".NULL",		Null,		0 },
224	{ ".OPTIONAL",		Attribute,	OP_OPTIONAL },
225	{ ".ORDER",		Order,		0 },
226	{ ".PARALLEL",		Parallel,	0 },
227	{ ".PATH",		ExPath,		0 },
228	{ ".PHONY",		Phony,		OP_PHONY },
229	{ ".POSIX",		Posix,		0 },
230	{ ".PRECIOUS",		Precious,	OP_PRECIOUS },
231	{ ".RECURSIVE",		Attribute,	OP_MAKE },
232	{ ".SHELL",		ExShell,	0 },
233	{ ".SILENT",		Silent,		OP_SILENT },
234	{ ".SINGLESHELL",	SingleShell,	0 },
235	{ ".SUFFIXES",		Suffixes,	0 },
236	{ ".USE",		Attribute,	OP_USE },
237	{ ".WAIT",		Wait,		0 },
238	{ ".WARN",		Warn,		0 },
239	/* KEYWORD-END-TAG */
240};
241#define	NKEYWORDS	(sizeof(parseKeywords) / sizeof(parseKeywords[0]))
242
243static void parse_include(char *, int, int);
244static void parse_sinclude(char *, int, int);
245static void parse_message(char *, int, int);
246static void parse_undef(char *, int, int);
247static void parse_for(char *, int, int);
248static void parse_endfor(char *, int, int);
249
250static const struct directive {
251	const char	*name;
252	int		code;
253	Boolean		skip_flag;	/* execute even when skipped */
254	void		(*func)(char *, int, int);
255} directives[] = {
256	/* DIRECTIVES-START-TAG */
257	{ "elif",	COND_ELIF,	TRUE,	Cond_If },
258	{ "elifdef",	COND_ELIFDEF,	TRUE,	Cond_If },
259	{ "elifmake",	COND_ELIFMAKE,	TRUE,	Cond_If },
260	{ "elifndef",	COND_ELIFNDEF,	TRUE,	Cond_If },
261	{ "elifnmake",	COND_ELIFNMAKE,	TRUE,	Cond_If },
262	{ "else",	COND_ELSE,	TRUE,	Cond_Else },
263	{ "endfor",	0,		FALSE,	parse_endfor },
264	{ "endif",	COND_ENDIF,	TRUE,	Cond_Endif },
265	{ "error",	1,		FALSE,	parse_message },
266	{ "for",	0,		FALSE,	parse_for },
267	{ "if",		COND_IF,	TRUE,	Cond_If },
268	{ "ifdef",	COND_IFDEF,	TRUE,	Cond_If },
269	{ "ifmake",	COND_IFMAKE,	TRUE,	Cond_If },
270	{ "ifndef",	COND_IFNDEF,	TRUE,	Cond_If },
271	{ "ifnmake",	COND_IFNMAKE,	TRUE,	Cond_If },
272	{ "include",	0,		FALSE,	parse_include },
273	{ "sinclude",	0,		FALSE,	parse_sinclude },
274	{ "undef",	0,		FALSE,	parse_undef },
275	{ "warning",	0,		FALSE,	parse_message },
276	/* DIRECTIVES-END-TAG */
277};
278#define	NDIRECTS	(sizeof(directives) / sizeof(directives[0]))
279
280/*-
281 * ParseFindKeyword
282 *	Look in the table of keywords for one matching the given string.
283 *
284 * Results:
285 *	The pointer to keyword table entry or NULL.
286 */
287static const struct keyword *
288ParseFindKeyword(const char *str)
289{
290	int kw;
291
292	kw = keyword_hash(str, strlen(str));
293	if (kw < 0 || kw >= (int)NKEYWORDS ||
294	    strcmp(str, parseKeywords[kw].name) != 0)
295		return (NULL);
296	return (&parseKeywords[kw]);
297}
298
299/*-
300 * Parse_Error  --
301 *	Error message abort function for parsing. Prints out the context
302 *	of the error (line number and file) as well as the message with
303 *	two optional arguments.
304 *
305 * Results:
306 *	None
307 *
308 * Side Effects:
309 *	"fatals" is incremented if the level is PARSE_FATAL.
310 */
311/* VARARGS */
312void
313Parse_Error(int type, const char *fmt, ...)
314{
315	va_list ap;
316
317	va_start(ap, fmt);
318	if (CURFILE != NULL)
319		fprintf(stderr, "\"%s\", line %d: ",
320		    CURFILE->fname, CURFILE->lineno);
321	if (type == PARSE_WARNING)
322		fprintf(stderr, "warning: ");
323	vfprintf(stderr, fmt, ap);
324	va_end(ap);
325	fprintf(stderr, "\n");
326	fflush(stderr);
327	if (type == PARSE_FATAL)
328		fatals += 1;
329}
330
331/**
332 * ParsePushInput
333 *
334 * Push a new input source onto the input stack. If ptr is NULL
335 * the fullname is used to fopen the file. If it is not NULL,
336 * ptr is assumed to point to the string to be parsed. If opening the
337 * file fails, the fullname is freed.
338 */
339static void
340ParsePushInput(char *fullname, FILE *fp, char *ptr, int lineno)
341{
342	struct IFile *nf;
343
344	nf = emalloc(sizeof(*nf));
345	nf->fname = fullname;
346	nf->lineno = lineno;
347
348	if (ptr == NULL) {
349		/* the input source is a file */
350		if ((nf->F = fp) == NULL) {
351			nf->F = fopen(fullname, "r");
352			if (nf->F == NULL) {
353				Parse_Error(PARSE_FATAL, "Cannot open %s",
354				    fullname);
355				free(fullname);
356				free(nf);
357				return;
358			}
359		}
360		nf->str = nf->ptr = NULL;
361		Var_Append(".MAKEFILE_LIST", fullname, VAR_GLOBAL);
362	} else {
363		nf->str = nf->ptr = ptr;
364		nf->F = NULL;
365	}
366	TAILQ_INSERT_HEAD(&includes, nf, link);
367}
368
369/**
370 * ParsePopInput
371 *	Called when EOF is reached in the current file. If we were reading
372 *	an include file, the includes stack is popped and things set up
373 *	to go back to reading the previous file at the previous location.
374 *
375 * Results:
376 *	CONTINUE if there's more to do. DONE if not.
377 *
378 * Side Effects:
379 *	The old curFile.F is closed. The includes list is shortened.
380 *	curFile.lineno, curFile.F, and curFile.fname are changed if
381 *	CONTINUE is returned.
382 */
383static int
384ParsePopInput(void)
385{
386	struct IFile *ifile;	/* the state on the top of the includes stack */
387
388	assert(!TAILQ_EMPTY(&includes));
389
390	ifile = TAILQ_FIRST(&includes);
391	TAILQ_REMOVE(&includes, ifile, link);
392
393	free(ifile->fname);
394	if (ifile->F != NULL) {
395		fclose(ifile->F);
396		Var_Append(".MAKEFILE_LIST", "..", VAR_GLOBAL);
397	}
398	if (ifile->str != NULL) {
399		free(ifile->str);
400	}
401	free(ifile);
402
403	return (TAILQ_EMPTY(&includes) ? DONE : CONTINUE);
404}
405
406/**
407 * parse_warn
408 *	Parse the .WARN pseudo-target.
409 */
410static void
411parse_warn(char *line)
412{
413	ArgArray	aa;
414	int		i;
415
416	brk_string(&aa, line, TRUE);
417
418	for (i = 1; i < aa.argc; i++)
419		Main_ParseWarn(aa.argv[i], 0);
420}
421
422/*-
423 *---------------------------------------------------------------------
424 * ParseLinkSrc  --
425 *	Link the parent nodes to their new child. Used by
426 *	ParseDoDependency. If the specType isn't 'Not', the parent
427 *	isn't linked as a parent of the child.
428 *
429 * Side Effects:
430 *	New elements are added to the parents lists of cgn and the
431 *	children list of cgn. the unmade field of pgn is updated
432 *	to reflect the additional child.
433 *---------------------------------------------------------------------
434 */
435static void
436ParseLinkSrc(Lst *parents, GNode *cgn)
437{
438	LstNode	*ln;
439	GNode *pgn;
440
441	LST_FOREACH(ln, parents) {
442		pgn = Lst_Datum(ln);
443		if (Lst_Member(&pgn->children, cgn) == NULL) {
444			Lst_AtEnd(&pgn->children, cgn);
445			if (specType == Not) {
446				Lst_AtEnd(&cgn->parents, pgn);
447			}
448			pgn->unmade += 1;
449		}
450	}
451}
452
453/*-
454 *---------------------------------------------------------------------
455 * ParseDoOp  --
456 *	Apply the parsed operator to all target nodes. Used in
457 *	ParseDoDependency once all targets have been found and their
458 *	operator parsed. If the previous and new operators are incompatible,
459 *	a major error is taken.
460 *
461 * Side Effects:
462 *	The type field of the node is altered to reflect any new bits in
463 *	the op.
464 *---------------------------------------------------------------------
465 */
466static void
467ParseDoOp(int op)
468{
469	GNode	*cohort;
470	LstNode	*ln;
471	GNode	*gn;
472
473	LST_FOREACH(ln, &targets) {
474		gn = Lst_Datum(ln);
475
476		/*
477		 * If the dependency mask of the operator and the node don't
478		 * match and the node has actually had an operator applied to
479		 * it before, and the operator actually has some dependency
480		 * information in it, complain.
481		 */
482		if ((op & OP_OPMASK) != (gn->type & OP_OPMASK) &&
483		    !OP_NOP(gn->type) && !OP_NOP(op)) {
484			Parse_Error(PARSE_FATAL, "Inconsistent operator for %s",
485			    gn->name);
486			return;
487		}
488
489		if (op == OP_DOUBLEDEP &&
490		    (gn->type & OP_OPMASK) == OP_DOUBLEDEP) {
491			/*
492			 * If the node was the object of a :: operator, we need
493			 * to create a new instance of it for the children and
494			 * commands on this dependency line. The new instance
495			 * is placed on the 'cohorts' list of the initial one
496			 * (note the initial one is not on its own cohorts list)
497			 * and the new instance is linked to all parents of the
498			 * initial instance.
499			 */
500			cohort = Targ_NewGN(gn->name);
501
502			/*
503			 * Duplicate links to parents so graph traversal is
504			 * simple. Perhaps some type bits should be duplicated?
505			 *
506			 * Make the cohort invisible as well to avoid
507			 * duplicating it into other variables. True, parents
508			 * of this target won't tend to do anything with their
509			 * local variables, but better safe than sorry.
510			 */
511			ParseLinkSrc(&gn->parents, cohort);
512			cohort->type = OP_DOUBLEDEP|OP_INVISIBLE;
513			Lst_AtEnd(&gn->cohorts, cohort);
514
515			/*
516			 * Replace the node in the targets list with the
517			 * new copy
518			 */
519			Lst_Replace(ln, cohort);
520			gn = cohort;
521		}
522		/*
523		 * We don't want to nuke any previous flags (whatever they were)
524		 * so we just OR the new operator into the old
525		 */
526		gn->type |= op;
527	}
528}
529
530/*-
531 *---------------------------------------------------------------------
532 * ParseDoSrc  --
533 *	Given the name of a source, figure out if it is an attribute
534 *	and apply it to the targets if it is. Else decide if there is
535 *	some attribute which should be applied *to* the source because
536 *	of some special target and apply it if so. Otherwise, make the
537 *	source be a child of the targets in the list 'targets'
538 *
539 * Results:
540 *	None
541 *
542 * Side Effects:
543 *	Operator bits may be added to the list of targets or to the source.
544 *	The targets may have a new source added to their lists of children.
545 *---------------------------------------------------------------------
546 */
547static void
548ParseDoSrc(int tOp, char *src, Lst *allsrc)
549{
550	GNode	*gn = NULL;
551	const struct keyword *kw;
552
553	if (src[0] == '.' && isupper ((unsigned char)src[1])) {
554		if ((kw = ParseFindKeyword(src)) != NULL) {
555			if (kw->op != 0) {
556				ParseDoOp(kw->op);
557				return;
558			}
559			if (kw->spec == Wait) {
560				waiting++;
561				return;
562			}
563		}
564	}
565
566	switch (specType) {
567	  case Main:
568		/*
569		 * If we have noted the existence of a .MAIN, it means we need
570		 * to add the sources of said target to the list of things
571		 * to create. The string 'src' is likely to be free, so we
572		 * must make a new copy of it. Note that this will only be
573		 * invoked if the user didn't specify a target on the command
574		 * line. This is to allow #ifmake's to succeed, or something...
575		 */
576		Lst_AtEnd(&create, estrdup(src));
577		/*
578		 * Add the name to the .TARGETS variable as well, so the user
579		 * can employ that, if desired.
580		 */
581		Var_Append(".TARGETS", src, VAR_GLOBAL);
582		return;
583
584	  case Order:
585		/*
586		 * Create proper predecessor/successor links between the
587		 * previous source and the current one.
588		 */
589		gn = Targ_FindNode(src, TARG_CREATE);
590		if (predecessor != NULL) {
591			Lst_AtEnd(&predecessor->successors, gn);
592			Lst_AtEnd(&gn->preds, predecessor);
593		}
594		/*
595		 * The current source now becomes the predecessor for the next
596		 * one.
597		 */
598		predecessor = gn;
599		break;
600
601	  default:
602		/*
603		 * If the source is not an attribute, we need to find/create
604		 * a node for it. After that we can apply any operator to it
605		 * from a special target or link it to its parents, as
606		 * appropriate.
607		 *
608		 * In the case of a source that was the object of a :: operator,
609		 * the attribute is applied to all of its instances (as kept in
610		 * the 'cohorts' list of the node) or all the cohorts are linked
611		 * to all the targets.
612		 */
613		gn = Targ_FindNode(src, TARG_CREATE);
614		if (tOp) {
615			gn->type |= tOp;
616		} else {
617			ParseLinkSrc(&targets, gn);
618		}
619		if ((gn->type & OP_OPMASK) == OP_DOUBLEDEP) {
620			GNode	*cohort;
621			LstNode	*ln;
622
623			for (ln = Lst_First(&gn->cohorts); ln != NULL;
624			    ln = Lst_Succ(ln)) {
625				cohort = Lst_Datum(ln);
626				if (tOp) {
627					cohort->type |= tOp;
628				} else {
629					ParseLinkSrc(&targets, cohort);
630				}
631			}
632		}
633		break;
634	}
635
636	gn->order = waiting;
637	Lst_AtEnd(allsrc, gn);
638	if (waiting) {
639		LstNode	*ln;
640		GNode	*p;
641
642		/*
643		 * Check if GNodes needs to be synchronized.
644		 * This has to be when two nodes are on different sides of a
645		 * .WAIT directive.
646		 */
647		LST_FOREACH(ln, allsrc) {
648			p = Lst_Datum(ln);
649
650			if (p->order >= gn->order)
651				break;
652			/*
653			 * XXX: This can cause loops, and loops can cause
654			 * unmade targets, but checking is tedious, and the
655			 * debugging output can show the problem
656			 */
657			Lst_AtEnd(&p->successors, gn);
658			Lst_AtEnd(&gn->preds, p);
659		}
660	}
661}
662
663
664/*-
665 *---------------------------------------------------------------------
666 * ParseDoDependency  --
667 *	Parse the dependency line in line.
668 *
669 * Results:
670 *	None
671 *
672 * Side Effects:
673 *	The nodes of the sources are linked as children to the nodes of the
674 *	targets. Some nodes may be created.
675 *
676 *	We parse a dependency line by first extracting words from the line and
677 * finding nodes in the list of all targets with that name. This is done
678 * until a character is encountered which is an operator character. Currently
679 * these are only ! and :. At this point the operator is parsed and the
680 * pointer into the line advanced until the first source is encountered.
681 *	The parsed operator is applied to each node in the 'targets' list,
682 * which is where the nodes found for the targets are kept, by means of
683 * the ParseDoOp function.
684 *	The sources are read in much the same way as the targets were except
685 * that now they are expanded using the wildcarding scheme of the C-Shell
686 * and all instances of the resulting words in the list of all targets
687 * are found. Each of the resulting nodes is then linked to each of the
688 * targets as one of its children.
689 *	Certain targets are handled specially. These are the ones detailed
690 * by the specType variable.
691 *	The storing of transformation rules is also taken care of here.
692 * A target is recognized as a transformation rule by calling
693 * Suff_IsTransform. If it is a transformation rule, its node is gotten
694 * from the suffix module via Suff_AddTransform rather than the standard
695 * Targ_FindNode in the target module.
696 *---------------------------------------------------------------------
697 */
698static void
699ParseDoDependency(char *line)
700{
701	char	*cp;	/* our current position */
702	char	*lstart = line;	/* original input line */
703	GNode	*gn;	/* a general purpose temporary node */
704	int	op;	/* the operator on the line */
705	char	savec;	/* a place to save a character */
706	Lst	paths;	/* Search paths to alter when parsing .PATH targets */
707	int	tOp;	/* operator from special target */
708	LstNode	*ln;
709	const struct keyword *kw;
710
711	tOp = 0;
712
713	specType = Not;
714	waiting = 0;
715	Lst_Init(&paths);
716
717	do {
718		for (cp = line;
719		    *cp && !isspace((unsigned char)*cp) && *cp != '(';
720		    cp++) {
721			if (*cp == '$') {
722				/*
723				 * Must be a dynamic source (would have been
724				 * expanded otherwise), so call the Var module
725				 * to parse the puppy so we can safely advance
726				 * beyond it...There should be no errors in this
727				 * as they would have been discovered in the
728				 * initial Var_Subst and we wouldn't be here.
729				 */
730				size_t	length = 0;
731				Boolean	freeIt;
732				char	*result;
733
734				result = Var_Parse(cp, VAR_CMD, TRUE,
735				    &length, &freeIt);
736
737				if (freeIt) {
738					free(result);
739				}
740				cp += length - 1;
741
742			} else if (*cp == '!' || *cp == ':') {
743				/*
744				 * We don't want to end a word on ':' or '!' if
745				 * there is a better match later on in the
746				 * string (greedy matching).
747				 * This allows the user to have targets like:
748				 *    fie::fi:fo: fum
749				 *    foo::bar:
750				 * where "fie::fi:fo" and "foo::bar" are the
751				 * targets. In real life this is used for perl5
752				 * library man pages where "::" separates an
753				 * object from its class. Ie:
754				 * "File::Spec::Unix". This behaviour is also
755				 * consistent with other versions of make.
756				 */
757				char *p = cp + 1;
758
759				if (*cp == ':' && *p == ':')
760					p++;
761
762				/* Found the best match already. */
763				if (*p == '\0' || isspace(*p))
764					break;
765
766				p += strcspn(p, "!:");
767
768				/* No better match later on... */
769				if (*p == '\0')
770					break;
771			}
772			continue;
773		}
774		if (*cp == '(') {
775			/*
776			 * Archives must be handled specially to make sure the
777			 * OP_ARCHV flag is set in their 'type' field, for one
778			 * thing, and because things like "archive(file1.o
779			 * file2.o file3.o)" are permissible. Arch_ParseArchive
780			 * will set 'line' to be the first non-blank after the
781			 * archive-spec. It creates/finds nodes for the members
782			 * and places them on the given list, returning TRUE
783			 * if all went well and FALSE if there was an error in
784			 * the specification. On error, line should remain
785			 * untouched.
786			 */
787			if (!Arch_ParseArchive(&line, &targets, VAR_CMD)) {
788				Parse_Error(PARSE_FATAL,
789				    "Error in archive specification: \"%s\"",
790				    line);
791				return;
792			} else {
793				cp = line;
794				continue;
795			}
796		}
797		savec = *cp;
798
799		if (!*cp) {
800			/*
801			 * Ending a dependency line without an operator is a				 * Bozo no-no. As a heuristic, this is also often
802			 * triggered by undetected conflicts from cvs/rcs
803			 * merges.
804			 */
805			if (strncmp(line, "<<<<<<", 6) == 0 ||
806			    strncmp(line, "||||||", 6) == 0 ||
807			    strncmp(line, "======", 6) == 0 ||
808			    strncmp(line, ">>>>>>", 6) == 0) {
809				Parse_Error(PARSE_FATAL, "Makefile appears to "
810				    "contain unresolved cvs/rcs/??? merge "
811				    "conflicts");
812			} else
813				Parse_Error(PARSE_FATAL, lstart[0] == '.' ?
814				    "Unknown directive" : "Need an operator");
815			return;
816		}
817		*cp = '\0';
818		/*
819		 * Have a word in line. See if it's a special target and set
820		 * specType to match it.
821		 */
822		if (*line == '.' && isupper((unsigned char)line[1])) {
823			/*
824			 * See if the target is a special target that must have
825			 * it or its sources handled specially.
826			 */
827			if ((kw = ParseFindKeyword(line)) != NULL) {
828				if (specType == ExPath && kw->spec != ExPath) {
829					Parse_Error(PARSE_FATAL,
830					    "Mismatched special targets");
831					return;
832				}
833
834				specType = kw->spec;
835				tOp = kw->op;
836
837				/*
838				 * Certain special targets have special
839				 * semantics:
840				 *  .PATH	Have to set the dirSearchPath
841				 *		variable too
842				 *  .MAIN	Its sources are only used if
843				 *		nothing has been specified to
844				 *		create.
845				 *  .DEFAULT    Need to create a node to hang
846				 *		commands on, but we don't want
847				 *		it in the graph, nor do we want
848				 *		it to be the Main Target, so we
849				 *		create it, set OP_NOTMAIN and
850				 *		add it to the list, setting
851				 *		DEFAULT to the new node for
852				 *		later use. We claim the node is
853				 *		A transformation rule to make
854				 *		life easier later, when we'll
855				 *		use Make_HandleUse to actually
856				 *		apply the .DEFAULT commands.
857				 *  .PHONY	The list of targets
858				 *  .BEGIN
859				 *  .END
860				 *  .INTERRUPT	Are not to be considered the
861				 *		main target.
862				 *  .NOTPARALLEL Make only one target at a time.
863				 *  .SINGLESHELL Create a shell for each
864				 *		command.
865				 *  .ORDER	Must set initial predecessor
866				 *		to NULL
867				 */
868				switch (specType) {
869				  case ExPath:
870					Lst_AtEnd(&paths, &dirSearchPath);
871					break;
872				  case Main:
873					if (!Lst_IsEmpty(&create)) {
874						specType = Not;
875					}
876					break;
877				  case Begin:
878				  case End:
879				  case Interrupt:
880					gn = Targ_FindNode(line, TARG_CREATE);
881					gn->type |= OP_NOTMAIN;
882					Lst_AtEnd(&targets, gn);
883					break;
884				  case Default:
885					gn = Targ_NewGN(".DEFAULT");
886					gn->type |= (OP_NOTMAIN|OP_TRANSFORM);
887					Lst_AtEnd(&targets, gn);
888					DEFAULT = gn;
889					break;
890				  case NotParallel:
891					jobLimit = 1;
892					break;
893				  case SingleShell:
894					compatMake = 1;
895					break;
896				  case Order:
897					predecessor = NULL;
898					break;
899				  default:
900					break;
901				}
902
903			} else if (strncmp(line, ".PATH", 5) == 0) {
904				/*
905				 * .PATH<suffix> has to be handled specially.
906				 * Call on the suffix module to give us a path
907				 * to modify.
908				 */
909				struct Path *path;
910
911				specType = ExPath;
912				path = Suff_GetPath(&line[5]);
913				if (path == NULL) {
914					Parse_Error(PARSE_FATAL, "Suffix '%s' "
915					    "not defined (yet)", &line[5]);
916					return;
917				} else
918					Lst_AtEnd(&paths, path);
919			}
920		}
921
922		/*
923		 * Have word in line. Get or create its node and stick it at
924		 * the end of the targets list
925		 */
926		if (specType == Not && *line != '\0') {
927
928			/* target names to be found and added to targets list */
929			Lst curTargs = Lst_Initializer(curTargs);
930
931			if (Dir_HasWildcards(line)) {
932				/*
933				 * Targets are to be sought only in the current
934				 * directory, so create an empty path for the
935				 * thing. Note we need to use Path_Clear in the
936				 * destruction of the path as the Dir module
937				 * could have added a directory to the path...
938				 */
939				struct Path emptyPath =
940				    TAILQ_HEAD_INITIALIZER(emptyPath);
941
942				Path_Expand(line, &emptyPath, &curTargs);
943				Path_Clear(&emptyPath);
944
945			} else {
946				/*
947				 * No wildcards, but we want to avoid code
948				 * duplication, so create a list with the word
949				 * on it.
950				 */
951				Lst_AtEnd(&curTargs, line);
952			}
953
954			while (!Lst_IsEmpty(&curTargs)) {
955				char	*targName = Lst_DeQueue(&curTargs);
956
957				if (!Suff_IsTransform (targName)) {
958					gn = Targ_FindNode(targName,
959					    TARG_CREATE);
960				} else {
961					gn = Suff_AddTransform(targName);
962				}
963
964				Lst_AtEnd(&targets, gn);
965			}
966		} else if (specType == ExPath && *line != '.' && *line != '\0'){
967			Parse_Error(PARSE_WARNING, "Extra target (%s) ignored",
968			    line);
969		}
970
971		*cp = savec;
972		/*
973		 * If it is a special type and not .PATH, it's the only
974		 * target we allow on this line...
975		 */
976		if (specType != Not && specType != ExPath) {
977			Boolean warnFlag = FALSE;
978
979			while (*cp != '!' && *cp != ':' && *cp) {
980				if (*cp != ' ' && *cp != '\t') {
981					warnFlag = TRUE;
982				}
983				cp++;
984			}
985			if (warnFlag) {
986				Parse_Error(PARSE_WARNING,
987				    "Extra target ignored");
988			}
989		} else {
990			while (*cp && isspace((unsigned char)*cp)) {
991				cp++;
992			}
993		}
994		line = cp;
995	} while (*line != '!' && *line != ':' && *line);
996
997	if (!Lst_IsEmpty(&targets)) {
998		switch (specType) {
999		  default:
1000			Parse_Error(PARSE_WARNING, "Special and mundane "
1001			    "targets don't mix. Mundane ones ignored");
1002			break;
1003		  case Default:
1004		  case Begin:
1005		  case End:
1006		  case Interrupt:
1007			/*
1008			 * These four create nodes on which to hang commands, so
1009			 * targets shouldn't be empty...
1010			 */
1011		  case Not:
1012			/*
1013			 * Nothing special here -- targets can be empty if it
1014			 * wants.
1015			 */
1016			break;
1017		}
1018	}
1019
1020	/*
1021	 * Have now parsed all the target names. Must parse the operator next.
1022	 * The result is left in op.
1023	 */
1024	if (*cp == '!') {
1025		op = OP_FORCE;
1026	} else if (*cp == ':') {
1027		if (cp[1] == ':') {
1028			op = OP_DOUBLEDEP;
1029			cp++;
1030		} else {
1031			op = OP_DEPENDS;
1032		}
1033	} else {
1034		Parse_Error(PARSE_FATAL, lstart[0] == '.' ?
1035		    "Unknown directive" : "Missing dependency operator");
1036		return;
1037	}
1038
1039	cp++;			/* Advance beyond operator */
1040
1041	ParseDoOp(op);
1042
1043	/*
1044	 * Get to the first source
1045	 */
1046	while (*cp && isspace((unsigned char)*cp)) {
1047		cp++;
1048	}
1049	line = cp;
1050
1051	/*
1052	 * Several special targets take different actions if present with no
1053	 * sources:
1054	 *	a .SUFFIXES line with no sources clears out all old suffixes
1055	 *	a .PRECIOUS line makes all targets precious
1056	 *	a .IGNORE line ignores errors for all targets
1057	 *	a .SILENT line creates silence when making all targets
1058	 *	a .PATH removes all directories from the search path(s).
1059	 */
1060	if (!*line) {
1061		switch (specType) {
1062		  case Suffixes:
1063			Suff_ClearSuffixes();
1064			break;
1065		  case Precious:
1066			allPrecious = TRUE;
1067			break;
1068		  case Ignore:
1069			ignoreErrors = TRUE;
1070			break;
1071		  case Silent:
1072			beSilent = TRUE;
1073			break;
1074		  case ExPath:
1075			LST_FOREACH(ln, &paths)
1076			Path_Clear(Lst_Datum(ln));
1077			break;
1078		  case MakefileDeps:
1079			mfAutoDeps = TRUE;
1080			break;
1081		  case Posix:
1082			is_posix = TRUE;
1083			Var_SetGlobal("%POSIX", "1003.2");
1084			break;
1085		  default:
1086			break;
1087		}
1088
1089	} else if (specType == MFlags) {
1090		/*
1091		 * Call on functions in main.c to deal with these arguments and
1092		 * set the initial character to a null-character so the loop to
1093		 * get sources won't get anything
1094		 */
1095		Main_ParseArgLine(line, 0);
1096		*line = '\0';
1097
1098	} else if (specType == Warn) {
1099		parse_warn(line);
1100		*line = '\0';
1101
1102	} else if (specType == ExShell) {
1103		if (!Shell_Parse(line)) {
1104			Parse_Error(PARSE_FATAL,
1105			    "improper shell specification");
1106			return;
1107		}
1108		*line = '\0';
1109
1110	} else if (specType == NotParallel || specType == SingleShell) {
1111		*line = '\0';
1112	}
1113
1114	/*
1115	* NOW GO FOR THE SOURCES
1116	*/
1117	if (specType == Suffixes || specType == ExPath ||
1118	    specType == Includes || specType == Libs ||
1119	    specType == Null) {
1120		while (*line) {
1121			/*
1122			 * If the target was one that doesn't take files as its
1123			 * sources but takes something like suffixes, we take
1124			 * each space-separated word on the line as a something
1125			 * and deal with it accordingly.
1126			 *
1127			 * If the target was .SUFFIXES, we take each source as
1128			 * a suffix and add it to the list of suffixes
1129			 * maintained by the Suff module.
1130			 *
1131			 * If the target was a .PATH, we add the source as a
1132			 * directory to search on the search path.
1133			 *
1134			 * If it was .INCLUDES, the source is taken to be the
1135			 * suffix of files which will be #included and whose
1136			 * search path should be present in the .INCLUDES
1137			 * variable.
1138			 *
1139			 * If it was .LIBS, the source is taken to be the
1140			 * suffix of files which are considered libraries and
1141			 * whose search path should be present in the .LIBS
1142			 * variable.
1143			 *
1144			 * If it was .NULL, the source is the suffix to use
1145			 * when a file has no valid suffix.
1146			 */
1147			char  savech;
1148			while (*cp && !isspace((unsigned char)*cp)) {
1149				cp++;
1150			}
1151			savech = *cp;
1152			*cp = '\0';
1153			switch (specType) {
1154			  case Suffixes:
1155				Suff_AddSuffix(line);
1156				break;
1157			  case ExPath:
1158				LST_FOREACH(ln, &paths)
1159					Path_AddDir(Lst_Datum(ln), line);
1160				break;
1161			  case Includes:
1162				Suff_AddInclude(line);
1163				break;
1164			  case Libs:
1165				Suff_AddLib(line);
1166				break;
1167			  case Null:
1168				Suff_SetNull(line);
1169				break;
1170			  default:
1171				break;
1172			}
1173			*cp = savech;
1174			if (savech != '\0') {
1175				cp++;
1176			}
1177			while (*cp && isspace((unsigned char)*cp)) {
1178				cp++;
1179			}
1180			line = cp;
1181		}
1182		Lst_Destroy(&paths, NOFREE);
1183
1184	} else if (specType == ExportVar) {
1185		Var_SetEnv(line, VAR_GLOBAL);
1186
1187	} else {
1188		/* list of sources in order */
1189		Lst curSrcs = Lst_Initializer(curSrc);
1190
1191		while (*line) {
1192			/*
1193			 * The targets take real sources, so we must beware of
1194			 * archive specifications (i.e. things with left
1195			 * parentheses in them) and handle them accordingly.
1196			 */
1197			while (*cp && !isspace((unsigned char)*cp)) {
1198				if (*cp == '(' && cp > line && cp[-1] != '$') {
1199					/*
1200					 * Only stop for a left parenthesis if
1201					 * it isn't at the start of a word
1202					 * (that'll be for variable changes
1203					 * later) and isn't preceded by a dollar
1204					 * sign (a dynamic source).
1205					 */
1206					break;
1207				} else {
1208					cp++;
1209				}
1210			}
1211
1212			if (*cp == '(') {
1213				GNode	  *gnp;
1214
1215				/* list of archive source names after exp. */
1216				Lst sources = Lst_Initializer(sources);
1217
1218				if (!Arch_ParseArchive(&line, &sources,
1219				    VAR_CMD)) {
1220					Parse_Error(PARSE_FATAL, "Error in "
1221					    "source archive spec \"%s\"", line);
1222					return;
1223				}
1224
1225				while (!Lst_IsEmpty(&sources)) {
1226					gnp = Lst_DeQueue(&sources);
1227					ParseDoSrc(tOp, gnp->name, &curSrcs);
1228				}
1229				cp = line;
1230			} else {
1231				if (*cp) {
1232					*cp = '\0';
1233					cp += 1;
1234				}
1235
1236				ParseDoSrc(tOp, line, &curSrcs);
1237			}
1238			while (*cp && isspace((unsigned char)*cp)) {
1239				cp++;
1240			}
1241			line = cp;
1242		}
1243		Lst_Destroy(&curSrcs, NOFREE);
1244	}
1245
1246	if (mainNode == NULL) {
1247		/*
1248		 * If we have yet to decide on a main target to make, in the
1249		 * absence of any user input, we want the first target on
1250		 * the first dependency line that is actually a real target
1251		 * (i.e. isn't a .USE or .EXEC rule) to be made.
1252		 */
1253		LST_FOREACH(ln, &targets) {
1254			gn = Lst_Datum(ln);
1255			if ((gn->type & (OP_NOTMAIN | OP_USE |
1256			    OP_EXEC | OP_TRANSFORM)) == 0) {
1257				mainNode = gn;
1258				Targ_SetMain(gn);
1259				break;
1260			}
1261		}
1262	}
1263}
1264
1265/*-
1266 *---------------------------------------------------------------------
1267 * Parse_IsVar  --
1268 *	Return TRUE if the passed line is a variable assignment. A variable
1269 *	assignment consists of a single word followed by optional whitespace
1270 *	followed by either a += or an = operator.
1271 *	This function is used both by the Parse_File function and main when
1272 *	parsing the command-line arguments.
1273 *
1274 * Results:
1275 *	TRUE if it is. FALSE if it ain't
1276 *
1277 * Side Effects:
1278 *	none
1279 *---------------------------------------------------------------------
1280 */
1281Boolean
1282Parse_IsVar(char *line)
1283{
1284	Boolean wasSpace = FALSE;	/* set TRUE if found a space */
1285	Boolean haveName = FALSE;	/* Set TRUE if have a variable name */
1286
1287	int level = 0;
1288#define	ISEQOPERATOR(c) \
1289	((c) == '+' || (c) == ':' || (c) == '?' || (c) == '!')
1290
1291	/*
1292	 * Skip to variable name
1293	 */
1294	for (; *line == ' ' || *line == '\t'; line++)
1295		continue;
1296
1297	for (; *line != '=' || level != 0; line++) {
1298		switch (*line) {
1299		  case '\0':
1300			/*
1301			 * end-of-line -- can't be a variable assignment.
1302			 */
1303			return (FALSE);
1304
1305		  case ' ':
1306		  case '\t':
1307			/*
1308			 * there can be as much white space as desired so long
1309			 * as there is only one word before the operator
1310			*/
1311			wasSpace = TRUE;
1312			break;
1313
1314		  case '(':
1315		  case '{':
1316			level++;
1317			break;
1318
1319		  case '}':
1320		  case ')':
1321			level--;
1322			break;
1323
1324		  default:
1325			if (wasSpace && haveName) {
1326				if (ISEQOPERATOR(*line)) {
1327					/*
1328					 * We must have a finished word
1329					 */
1330					if (level != 0)
1331						return (FALSE);
1332
1333					/*
1334					 * When an = operator [+?!:] is found,
1335					 * the next character must be an = or
1336					 * it ain't a valid assignment.
1337					 */
1338					if (line[1] == '=')
1339						return (haveName);
1340#ifdef SUNSHCMD
1341					/*
1342					 * This is a shell command
1343					 */
1344					if (strncmp(line, ":sh", 3) == 0)
1345						return (haveName);
1346#endif
1347				}
1348				/*
1349				 * This is the start of another word, so not
1350				 * assignment.
1351				 */
1352				return (FALSE);
1353
1354			} else {
1355				haveName = TRUE;
1356				wasSpace = FALSE;
1357			}
1358			break;
1359		}
1360	}
1361
1362	return (haveName);
1363}
1364
1365/*-
1366 *---------------------------------------------------------------------
1367 * Parse_DoVar  --
1368 *	Take the variable assignment in the passed line and do it in the
1369 *	global context.
1370 *
1371 *	Note: There is a lexical ambiguity with assignment modifier characters
1372 *	in variable names. This routine interprets the character before the =
1373 *	as a modifier. Therefore, an assignment like
1374 *	    C++=/usr/bin/CC
1375 *	is interpreted as "C+ +=" instead of "C++ =".
1376 *
1377 * Results:
1378 *	none
1379 *
1380 * Side Effects:
1381 *	the variable structure of the given variable name is altered in the
1382 *	global context.
1383 *---------------------------------------------------------------------
1384 */
1385void
1386Parse_DoVar(char *line, GNode *ctxt)
1387{
1388	char	*cp;	/* pointer into line */
1389	enum {
1390		VAR_SUBST,
1391		VAR_APPEND,
1392		VAR_SHELL,
1393		VAR_NORMAL
1394	}	type;	/* Type of assignment */
1395	char	*opc;	/* ptr to operator character to
1396			 * null-terminate the variable name */
1397
1398	/*
1399	 * Skip to variable name
1400	 */
1401	while (*line == ' ' || *line == '\t') {
1402		line++;
1403	}
1404
1405	/*
1406	 * Skip to operator character, nulling out whitespace as we go
1407	 */
1408	for (cp = line + 1; *cp != '='; cp++) {
1409		if (isspace((unsigned char)*cp)) {
1410			*cp = '\0';
1411		}
1412	}
1413	opc = cp - 1;		/* operator is the previous character */
1414	*cp++ = '\0';		/* nuke the = */
1415
1416	/*
1417	 * Check operator type
1418	 */
1419	switch (*opc) {
1420	  case '+':
1421		type = VAR_APPEND;
1422		*opc = '\0';
1423		break;
1424
1425	  case '?':
1426		/*
1427		 * If the variable already has a value, we don't do anything.
1428		 */
1429		*opc = '\0';
1430		if (Var_Exists(line, ctxt)) {
1431			return;
1432		} else {
1433			type = VAR_NORMAL;
1434		}
1435		break;
1436
1437	  case ':':
1438		type = VAR_SUBST;
1439		*opc = '\0';
1440		break;
1441
1442	  case '!':
1443		type = VAR_SHELL;
1444		*opc = '\0';
1445		break;
1446
1447	  default:
1448#ifdef SUNSHCMD
1449		while (*opc != ':') {
1450			if (opc == line)
1451				break;
1452			else
1453				--opc;
1454		}
1455
1456		if (strncmp(opc, ":sh", 3) == 0) {
1457			type = VAR_SHELL;
1458			*opc = '\0';
1459			break;
1460		}
1461#endif
1462		type = VAR_NORMAL;
1463		break;
1464	}
1465
1466	while (isspace((unsigned char)*cp)) {
1467		cp++;
1468	}
1469
1470	if (type == VAR_APPEND) {
1471		Var_Append(line, cp, ctxt);
1472
1473	} else if (type == VAR_SUBST) {
1474		/*
1475		 * Allow variables in the old value to be undefined, but leave
1476		 * their invocation alone -- this is done by forcing oldVars
1477		 * to be false.
1478		 * XXX: This can cause recursive variables, but that's not
1479		 * hard to do, and this allows someone to do something like
1480		 *
1481		 *  CFLAGS = $(.INCLUDES)
1482		 *  CFLAGS := -I.. $(CFLAGS)
1483		 *
1484		 * And not get an error.
1485		 */
1486		Boolean oldOldVars = oldVars;
1487
1488		oldVars = FALSE;
1489
1490		/*
1491		 * make sure that we set the variable the first time to nothing
1492		 * so that it gets substituted!
1493		 */
1494		if (!Var_Exists(line, ctxt))
1495			Var_Set(line, "", ctxt);
1496
1497		cp = Buf_Peel(Var_Subst(cp, ctxt, FALSE));
1498
1499		oldVars = oldOldVars;
1500
1501		Var_Set(line, cp, ctxt);
1502		free(cp);
1503
1504	} else if (type == VAR_SHELL) {
1505		/*
1506		 * TRUE if the command needs to be freed, i.e.
1507		 * if any variable expansion was performed
1508		 */
1509		Boolean	freeCmd = FALSE;
1510		Buffer *buf;
1511		const char *error;
1512
1513		if (strchr(cp, '$') != NULL) {
1514			/*
1515			 * There's a dollar sign in the command, so perform
1516			 * variable expansion on the whole thing. The
1517			 * resulting string will need freeing when we're done,
1518			 * so set freeCmd to TRUE.
1519			 */
1520			cp = Buf_Peel(Var_Subst(cp, VAR_CMD, TRUE));
1521			freeCmd = TRUE;
1522		}
1523
1524		buf = Cmd_Exec(cp, &error);
1525		Var_Set(line, Buf_Data(buf), ctxt);
1526		Buf_Destroy(buf, TRUE);
1527
1528		if (error)
1529			Parse_Error(PARSE_WARNING, error, cp);
1530
1531		if (freeCmd)
1532			free(cp);
1533
1534	} else {
1535		/*
1536		 * Normal assignment -- just do it.
1537		 */
1538		Var_Set(line, cp, ctxt);
1539	}
1540	if (strcmp(line, MAKE_JOB_PREFIX) == 0)
1541		Job_SetPrefix();
1542}
1543
1544/*-
1545 *-----------------------------------------------------------------------
1546 * ParseHasCommands --
1547 *	Callback procedure for Parse_File when destroying the list of
1548 *	targets on the last dependency line. Marks a target as already
1549 *	having commands if it does, to keep from having shell commands
1550 *	on multiple dependency lines.
1551 *
1552 * Results:
1553 *	None
1554 *
1555 * Side Effects:
1556 *	OP_HAS_COMMANDS may be set for the target.
1557 *
1558 *-----------------------------------------------------------------------
1559 */
1560static void
1561ParseHasCommands(void *gnp)
1562{
1563	GNode *gn = gnp;
1564
1565	if (!Lst_IsEmpty(&gn->commands)) {
1566		gn->type |= OP_HAS_COMMANDS;
1567	}
1568}
1569
1570/*-
1571 *-----------------------------------------------------------------------
1572 * Parse_AddIncludeDir --
1573 *	Add a directory to the path searched for included makefiles
1574 *	bracketed by double-quotes. Used by functions in main.c
1575 *
1576 * Results:
1577 *	None.
1578 *
1579 * Side Effects:
1580 *	The directory is appended to the list.
1581 *
1582 *-----------------------------------------------------------------------
1583 */
1584void
1585Parse_AddIncludeDir(char *dir)
1586{
1587
1588	Path_AddDir(&parseIncPath, dir);
1589}
1590
1591/*-
1592 *---------------------------------------------------------------------
1593 * Parse_FromString  --
1594 *	Start Parsing from the given string
1595 *
1596 * Results:
1597 *	None
1598 *
1599 * Side Effects:
1600 *	A structure is added to the includes Lst and readProc, curFile.lineno,
1601 *	curFile.fname and curFile.F are altered for the new file
1602 *---------------------------------------------------------------------
1603 */
1604void
1605Parse_FromString(char *str, int lineno)
1606{
1607
1608	DEBUGF(FOR, ("%s\n---- at line %d\n", str, lineno));
1609
1610	ParsePushInput(estrdup(CURFILE->fname), NULL, str, lineno);
1611}
1612
1613#ifdef SYSVINCLUDE
1614/*-
1615 *---------------------------------------------------------------------
1616 * ParseTraditionalInclude  --
1617 *	Push to another file.
1618 *
1619 *	The input is the line minus the "include".  The file name is
1620 *	the string following the "include".
1621 *
1622 * Results:
1623 *	None
1624 *
1625 * Side Effects:
1626 *	A structure is added to the includes Lst and readProc, curFile.lineno,
1627 *	curFile.fname and curFile.F are altered for the new file
1628 *---------------------------------------------------------------------
1629 */
1630static void
1631ParseTraditionalInclude(char *file)
1632{
1633	char	*fullname;	/* full pathname of file */
1634	char	*cp;		/* current position in file spec */
1635
1636	/*
1637	 * Skip over whitespace
1638	 */
1639	while (*file == ' ' || *file == '\t') {
1640		file++;
1641	}
1642
1643	if (*file == '\0') {
1644		Parse_Error(PARSE_FATAL, "Filename missing from \"include\"");
1645		return;
1646	}
1647
1648	/*
1649	* Skip to end of line or next whitespace
1650	*/
1651	for (cp = file; *cp && *cp != '\n' && *cp != '\t' && *cp != ' '; cp++) {
1652		continue;
1653	}
1654
1655	*cp = '\0';
1656
1657	/*
1658	 * Substitute for any variables in the file name before trying to
1659	 * find the thing.
1660	 */
1661	file = Buf_Peel(Var_Subst(file, VAR_CMD, FALSE));
1662
1663	/*
1664	 * Now we know the file's name, we attempt to find the durn thing.
1665	 * Search for it first on the -I search path, then on the .PATH
1666	 * search path, if not found in a -I directory.
1667	 */
1668	fullname = Path_FindFile(file, &parseIncPath);
1669	if (fullname == NULL) {
1670		fullname = Path_FindFile(file, &dirSearchPath);
1671	}
1672
1673	if (fullname == NULL) {
1674		/*
1675		 * Still haven't found the makefile. Look for it on the system
1676		 * path as a last resort.
1677		 */
1678		fullname = Path_FindFile(file, &sysIncPath);
1679	}
1680
1681	if (fullname == NULL) {
1682		Parse_Error(PARSE_FATAL, "Could not find %s", file);
1683		/* XXXHB free(file) */
1684		return;
1685	}
1686
1687	/* XXXHB free(file) */
1688
1689	/*
1690	 * We set up the name of the file to be the absolute
1691	 * name of the include file so error messages refer to the right
1692	 * place.
1693	 */
1694	ParsePushInput(fullname, NULL, NULL, 0);
1695}
1696#endif
1697
1698/*-
1699 *---------------------------------------------------------------------
1700 * ParseReadc  --
1701 *	Read a character from the current file
1702 *
1703 * Results:
1704 *	The character that was read
1705 *
1706 * Side Effects:
1707 *---------------------------------------------------------------------
1708 */
1709static int
1710ParseReadc(void)
1711{
1712
1713	if (CURFILE->F != NULL)
1714		return (fgetc(CURFILE->F));
1715
1716	if (CURFILE->str != NULL && *CURFILE->ptr != '\0')
1717		return (*CURFILE->ptr++);
1718
1719	return (EOF);
1720}
1721
1722
1723/*-
1724 *---------------------------------------------------------------------
1725 * ParseUnreadc  --
1726 *	Put back a character to the current file
1727 *
1728 * Results:
1729 *	None.
1730 *
1731 * Side Effects:
1732 *---------------------------------------------------------------------
1733 */
1734static void
1735ParseUnreadc(int c)
1736{
1737
1738	if (CURFILE->F != NULL) {
1739		ungetc(c, CURFILE->F);
1740		return;
1741	}
1742	if (CURFILE->str != NULL) {
1743		*--(CURFILE->ptr) = c;
1744		return;
1745	}
1746}
1747
1748/* ParseSkipLine():
1749 *	Grab the next line unless it begins with a dot (`.') and we're told to
1750 *	ignore such lines.
1751 */
1752static char *
1753ParseSkipLine(int skip, int keep_newline)
1754{
1755	char *line;
1756	int c, lastc;
1757	Buffer *buf;
1758
1759	buf = Buf_Init(MAKE_BSIZE);
1760
1761	do {
1762		Buf_Clear(buf);
1763		lastc = '\0';
1764
1765		while (((c = ParseReadc()) != '\n' || lastc == '\\')
1766		    && c != EOF) {
1767			if (skip && c == '#' && lastc != '\\') {
1768				/*
1769				 * let a comment be terminated even by an
1770				 * escaped \n. This is consistent to comment
1771				 * handling in ParseReadLine
1772				 */
1773				while ((c = ParseReadc()) != '\n' && c != EOF)
1774					;
1775				break;
1776			}
1777			if (c == '\n') {
1778				if (keep_newline)
1779					Buf_AddByte(buf, (Byte)c);
1780				else
1781					Buf_ReplaceLastByte(buf, (Byte)' ');
1782				CURFILE->lineno++;
1783
1784				while ((c = ParseReadc()) == ' ' || c == '\t')
1785					continue;
1786
1787				if (c == EOF)
1788					break;
1789			}
1790
1791			Buf_AddByte(buf, (Byte)c);
1792			lastc = c;
1793		}
1794
1795		if (c == EOF) {
1796			Parse_Error(PARSE_FATAL,
1797			    "Unclosed conditional/for loop");
1798			Buf_Destroy(buf, TRUE);
1799			return (NULL);
1800		}
1801
1802		CURFILE->lineno++;
1803		Buf_AddByte(buf, (Byte)'\0');
1804		line = Buf_Data(buf);
1805	} while (skip == 1 && line[0] != '.');
1806
1807	Buf_Destroy(buf, FALSE);
1808	return (line);
1809}
1810
1811/*-
1812 *---------------------------------------------------------------------
1813 * ParseReadLine --
1814 *	Read an entire line from the input file. Called only by Parse_File.
1815 *	To facilitate escaped newlines and what have you, a character is
1816 *	buffered in 'lastc', which is '\0' when no characters have been
1817 *	read. When we break out of the loop, c holds the terminating
1818 *	character and lastc holds a character that should be added to
1819 *	the line (unless we don't read anything but a terminator).
1820 *
1821 * Results:
1822 *	A line w/o its newline
1823 *
1824 * Side Effects:
1825 *	Only those associated with reading a character
1826 *---------------------------------------------------------------------
1827 */
1828static char *
1829ParseReadLine(void)
1830{
1831	Buffer	*buf;		/* Buffer for current line */
1832	int	c;		/* the current character */
1833	int	lastc;		/* The most-recent character */
1834	Boolean	semiNL;		/* treat semi-colons as newlines */
1835	Boolean	ignDepOp;	/* TRUE if should ignore dependency operators
1836				 * for the purposes of setting semiNL */
1837	Boolean	ignComment;	/* TRUE if should ignore comments (in a
1838				 * shell command */
1839	char	*line;		/* Result */
1840	char	*ep;		/* to strip trailing blanks */
1841
1842  again:
1843	semiNL = FALSE;
1844	ignDepOp = FALSE;
1845	ignComment = FALSE;
1846
1847	lastc = '\0';
1848
1849	/*
1850	 * Handle tab at the beginning of the line. A leading tab (shell
1851	 * command) forces us to ignore comments and dependency operators and
1852	 * treat semi-colons as semi-colons (by leaving semiNL FALSE).
1853	 * This also discards completely blank lines.
1854	 */
1855	for (;;) {
1856		c = ParseReadc();
1857		if (c == EOF) {
1858			if (ParsePopInput() == DONE) {
1859				/* End of all inputs - return NULL */
1860				return (NULL);
1861			}
1862			continue;
1863		}
1864
1865		if (c == '\t') {
1866			ignComment = ignDepOp = TRUE;
1867			lastc = c;
1868			break;
1869		}
1870		if (c != '\n') {
1871			ParseUnreadc(c);
1872			break;
1873		}
1874		CURFILE->lineno++;
1875	}
1876
1877	buf = Buf_Init(MAKE_BSIZE);
1878
1879	while (((c = ParseReadc()) != '\n' || lastc == '\\') && c != EOF) {
1880  test_char:
1881		switch (c) {
1882		  case '\n':
1883			/*
1884			 * Escaped newline: read characters until a
1885			 * non-space or an unescaped newline and
1886			 * replace them all by a single space. This is
1887			 * done by storing the space over the backslash
1888			 * and dropping through with the next nonspace.
1889			 * If it is a semi-colon and semiNL is TRUE,
1890			 * it will be recognized as a newline in the
1891			 * code below this...
1892			 */
1893			CURFILE->lineno++;
1894			lastc = ' ';
1895			while ((c = ParseReadc()) == ' ' || c == '\t') {
1896				continue;
1897			}
1898			if (c == EOF || c == '\n') {
1899				goto line_read;
1900			} else {
1901				/*
1902				 * Check for comments, semiNL's, etc. --
1903				 * easier than ParseUnreadc(c);
1904				 * continue;
1905				 */
1906				goto test_char;
1907			}
1908			/*NOTREACHED*/
1909			break;
1910
1911		  case ';':
1912			/*
1913			 * Semi-colon: Need to see if it should be
1914			 * interpreted as a newline
1915			 */
1916			if (semiNL) {
1917				/*
1918				 * To make sure the command that may
1919				 * be following this semi-colon begins
1920				 * with a tab, we push one back into the
1921				 * input stream. This will overwrite the
1922				 * semi-colon in the buffer. If there is
1923				 * no command following, this does no
1924				 * harm, since the newline remains in
1925				 * the buffer and the
1926				 * whole line is ignored.
1927				 */
1928				ParseUnreadc('\t');
1929				goto line_read;
1930			}
1931			break;
1932		  case '=':
1933			if (!semiNL) {
1934				/*
1935				 * Haven't seen a dependency operator
1936				 * before this, so this must be a
1937				 * variable assignment -- don't pay
1938				 * attention to dependency operators
1939				 * after this.
1940				 */
1941				ignDepOp = TRUE;
1942			} else if (lastc == ':' || lastc == '!') {
1943				/*
1944				 * Well, we've seen a dependency
1945				 * operator already, but it was the
1946				 * previous character, so this is really
1947				 * just an expanded variable assignment.
1948				 * Revert semi-colons to being just
1949				 * semi-colons again and ignore any more
1950				 * dependency operators.
1951				 *
1952				 * XXX: Note that a line like
1953				 * "foo : a:=b" will blow up, but who'd
1954				 * write a line like that anyway?
1955				 */
1956				ignDepOp = TRUE;
1957				semiNL = FALSE;
1958			}
1959			break;
1960		  case '#':
1961			if (!ignComment) {
1962				if (lastc != '\\') {
1963					/*
1964					 * If the character is a hash
1965					 * mark and it isn't escaped
1966					 * (or we're being compatible),
1967					 * the thing is a comment.
1968					 * Skip to the end of the line.
1969					 */
1970					do {
1971						c = ParseReadc();
1972					} while (c != '\n' && c != EOF);
1973					goto line_read;
1974				} else {
1975					/*
1976					 * Don't add the backslash.
1977					 * Just let the # get copied
1978					 * over.
1979					 */
1980					lastc = c;
1981					continue;
1982				}
1983			}
1984			break;
1985
1986		  case ':':
1987		  case '!':
1988			if (!ignDepOp) {
1989				/*
1990				 * A semi-colon is recognized as a
1991				 * newline only on dependency lines.
1992				 * Dependency lines are lines with a
1993				 * colon or an exclamation point.
1994				 * Ergo...
1995				 */
1996				semiNL = TRUE;
1997			}
1998			break;
1999
2000		  default:
2001			break;
2002		}
2003		/*
2004		 * Copy in the previous character (there may be none if this
2005		 * was the first character) and save this one in
2006		 * lastc.
2007		 */
2008		if (lastc != '\0')
2009			Buf_AddByte(buf, (Byte)lastc);
2010		lastc = c;
2011	}
2012  line_read:
2013	CURFILE->lineno++;
2014
2015	if (lastc != '\0') {
2016		Buf_AddByte(buf, (Byte)lastc);
2017	}
2018	Buf_AddByte(buf, (Byte)'\0');
2019	line = Buf_Peel(buf);
2020
2021	/*
2022	 * Strip trailing blanks and tabs from the line.
2023	 * Do not strip a blank or tab that is preceded by
2024	 * a '\'
2025	 */
2026	ep = line;
2027	while (*ep)
2028		++ep;
2029	while (ep > line + 1 && (ep[-1] == ' ' || ep[-1] == '\t')) {
2030		if (ep > line + 1 && ep[-2] == '\\')
2031			break;
2032		--ep;
2033	}
2034	*ep = 0;
2035
2036	if (line[0] == '\0') {
2037		/* empty line - just ignore */
2038		free(line);
2039		goto again;
2040	}
2041
2042	return (line);
2043}
2044
2045/*-
2046 *-----------------------------------------------------------------------
2047 * ParseFinishLine --
2048 *	Handle the end of a dependency group.
2049 *
2050 * Results:
2051 *	Nothing.
2052 *
2053 * Side Effects:
2054 *	inLine set FALSE. 'targets' list destroyed.
2055 *
2056 *-----------------------------------------------------------------------
2057 */
2058static void
2059ParseFinishLine(void)
2060{
2061	const LstNode	*ln;
2062
2063	if (inLine) {
2064		LST_FOREACH(ln, &targets) {
2065			if (((const GNode *)Lst_Datum(ln))->type & OP_TRANSFORM)
2066				Suff_EndTransform(Lst_Datum(ln));
2067		}
2068		Lst_Destroy(&targets, ParseHasCommands);
2069		inLine = FALSE;
2070	}
2071}
2072
2073/**
2074 * xparse_include
2075 *	Parse an .include directive and push the file onto the input stack.
2076 *	The input is the line minus the .include. A file spec is a string
2077 *	enclosed in <> or "". The former is looked for only in sysIncPath.
2078 *	The latter in . and the directories specified by -I command line
2079 *	options
2080 */
2081static void
2082xparse_include(char *file, int sinclude)
2083{
2084	char	*fullname;	/* full pathname of file */
2085	char	endc;		/* the character which ends the file spec */
2086	char	*cp;		/* current position in file spec */
2087	Boolean	isSystem;	/* TRUE if makefile is a system makefile */
2088	char	*prefEnd, *Fname;
2089	char	*newName;
2090
2091	/*
2092	 * Skip to delimiter character so we know where to look
2093	 */
2094	while (*file == ' ' || *file == '\t') {
2095		file++;
2096	}
2097
2098	if (*file != '"' && *file != '<') {
2099		Parse_Error(PARSE_FATAL,
2100		    ".include filename must be delimited by '\"' or '<'");
2101		return;
2102	}
2103
2104	/*
2105	 * Set the search path on which to find the include file based on the
2106	 * characters which bracket its name. Angle-brackets imply it's
2107	 * a system Makefile while double-quotes imply it's a user makefile
2108	 */
2109	if (*file == '<') {
2110		isSystem = TRUE;
2111		endc = '>';
2112	} else {
2113		isSystem = FALSE;
2114		endc = '"';
2115	}
2116
2117	/*
2118	* Skip to matching delimiter
2119	*/
2120	for (cp = ++file; *cp != endc; cp++) {
2121		if (*cp == '\0') {
2122			Parse_Error(PARSE_FATAL,
2123			    "Unclosed .include filename. '%c' expected", endc);
2124			return;
2125		}
2126	}
2127	*cp = '\0';
2128
2129	/*
2130	 * Substitute for any variables in the file name before trying to
2131	 * find the thing.
2132	 */
2133	file = Buf_Peel(Var_Subst(file, VAR_CMD, FALSE));
2134
2135	/*
2136	 * Now we know the file's name and its search path, we attempt to
2137	 * find the durn thing. A return of NULL indicates the file don't
2138	 * exist.
2139	 */
2140	if (!isSystem) {
2141		/*
2142		 * Include files contained in double-quotes are first searched
2143		 * for relative to the including file's location. We don't want
2144		 * to cd there, of course, so we just tack on the old file's
2145		 * leading path components and call Path_FindFile to see if
2146		 * we can locate the beast.
2147		 */
2148
2149		/* Make a temporary copy of this, to be safe. */
2150		Fname = estrdup(CURFILE->fname);
2151
2152		prefEnd = strrchr(Fname, '/');
2153		if (prefEnd != NULL) {
2154			*prefEnd = '\0';
2155			if (file[0] == '/')
2156				newName = estrdup(file);
2157			else
2158				newName = str_concat(Fname, file, STR_ADDSLASH);
2159			fullname = Path_FindFile(newName, &parseIncPath);
2160			if (fullname == NULL) {
2161				fullname = Path_FindFile(newName,
2162				    &dirSearchPath);
2163			}
2164			free(newName);
2165			*prefEnd = '/';
2166		} else {
2167			fullname = NULL;
2168		}
2169		free(Fname);
2170		if (fullname == NULL) {
2171			/*
2172			 * Makefile wasn't found in same directory as included
2173			 * makefile. Search for it first on the -I search path,
2174			 * then on the .PATH search path, if not found in a -I
2175			 * directory.
2176			 * XXX: Suffix specific?
2177			 */
2178			fullname = Path_FindFile(file, &parseIncPath);
2179			if (fullname == NULL) {
2180				fullname = Path_FindFile(file, &dirSearchPath);
2181			}
2182		}
2183	} else {
2184		fullname = NULL;
2185	}
2186
2187	if (fullname == NULL) {
2188		/*
2189		 * System makefile or still haven't found the makefile.
2190		 * Look for it on the system path.
2191		 */
2192		fullname = Path_FindFile(file, &sysIncPath);
2193	}
2194
2195	if (fullname == NULL) {
2196		*cp = endc;
2197		if (!sinclude)
2198			Parse_Error(PARSE_FATAL, "Could not find %s", file);
2199		else
2200			Main_AddSourceMakefile(file);
2201		free(file);
2202		return;
2203	}
2204	Main_AddSourceMakefile(fullname);
2205	free(file);
2206
2207	/*
2208	 * We set up the name of the file to be the absolute
2209	 * name of the include file so error messages refer to the right
2210	 * place.
2211	 */
2212	ParsePushInput(fullname, NULL, NULL, 0);
2213	DEBUGF(DIR, (".include %s\n", fullname));
2214}
2215
2216static void
2217parse_include(char *file, int code __unused, int lineno __unused)
2218{
2219	xparse_include(file, 0);
2220}
2221
2222static void
2223parse_sinclude(char *file, int code __unused, int lineno __unused)
2224{
2225	xparse_include(file, 1);
2226}
2227
2228/**
2229 * parse_message
2230 *	Parse a .warning or .error directive
2231 *
2232 *	The input is the line minus the ".error"/".warning".  We substitute
2233 *	variables, print the message and exit(1) (for .error) or just print
2234 *	a warning if the directive is malformed.
2235 */
2236static void
2237parse_message(char *line, int iserror, int lineno __unused)
2238{
2239
2240	if (!isspace((u_char)*line)) {
2241		Parse_Error(PARSE_WARNING, "invalid syntax: .%s%s",
2242		    iserror ? "error" : "warning", line);
2243		return;
2244	}
2245
2246	while (isspace((u_char)*line))
2247		line++;
2248
2249	line = Buf_Peel(Var_Subst(line, VAR_CMD, FALSE));
2250	Parse_Error(iserror ? PARSE_FATAL : PARSE_WARNING, "%s", line);
2251	free(line);
2252
2253	if (iserror) {
2254		/* Terminate immediately. */
2255		exit(1);
2256	}
2257}
2258
2259/**
2260 * parse_undef
2261 *	Parse an .undef directive.
2262 */
2263static void
2264parse_undef(char *line, int code __unused, int lineno __unused)
2265{
2266	char *cp;
2267
2268	while (isspace((u_char)*line))
2269		line++;
2270
2271	for (cp = line; !isspace((u_char)*cp) && *cp != '\0'; cp++) {
2272		;
2273	}
2274	*cp = '\0';
2275
2276	cp = Buf_Peel(Var_Subst(line, VAR_CMD, FALSE));
2277	Var_Delete(cp, VAR_GLOBAL);
2278	free(cp);
2279}
2280
2281/**
2282 * parse_for
2283 *	Parse a .for directive.
2284 */
2285static void
2286parse_for(char *line, int code __unused, int lineno)
2287{
2288
2289	if (!For_For(line)) {
2290		/* syntax error */
2291		return;
2292	}
2293	line = NULL;
2294
2295	/*
2296	 * Skip after the matching endfor.
2297	 */
2298	do {
2299		free(line);
2300		line = ParseSkipLine(0, 1);
2301		if (line == NULL) {
2302			Parse_Error(PARSE_FATAL,
2303			    "Unexpected end of file in for loop.\n");
2304			return;
2305		}
2306	} while (For_Eval(line));
2307	free(line);
2308
2309	/* execute */
2310	For_Run(lineno);
2311}
2312
2313/**
2314 * parse_endfor
2315 *	Parse endfor. This may only happen if there was no matching .for.
2316 */
2317static void
2318parse_endfor(char *line __unused, int code __unused, int lineno __unused)
2319{
2320
2321	Parse_Error(PARSE_FATAL, "for-less endfor");
2322}
2323
2324/**
2325 * parse_directive
2326 *	Got a line starting with a '.'. Check if this is a directive
2327 *	and parse it.
2328 *
2329 * return:
2330 *	TRUE if line was a directive, FALSE otherwise.
2331 */
2332static Boolean
2333parse_directive(char *line)
2334{
2335	char	*start;
2336	char	*cp;
2337	int	dir;
2338
2339	/*
2340	 * Get the keyword:
2341	 *	.[[:space:]]*\([[:alpha:]][[:alnum:]_]*\).*
2342	 * \1 is the keyword.
2343	 */
2344	for (start = line; isspace((u_char)*start); start++) {
2345		;
2346	}
2347
2348	if (!isalpha((u_char)*start)) {
2349		return (FALSE);
2350	}
2351
2352	cp = start + 1;
2353	while (isalnum((u_char)*cp) || *cp == '_') {
2354		cp++;
2355	}
2356
2357	dir = directive_hash(start, cp - start);
2358	if (dir < 0 || dir >= (int)NDIRECTS ||
2359	    (size_t)(cp - start) != strlen(directives[dir].name) ||
2360	    strncmp(start, directives[dir].name, cp - start) != 0) {
2361		/* not actually matched */
2362		return (FALSE);
2363	}
2364
2365	if (!skipLine || directives[dir].skip_flag)
2366		(*directives[dir].func)(cp, directives[dir].code,
2367		    CURFILE->lineno);
2368	return (TRUE);
2369}
2370
2371/*-
2372 *---------------------------------------------------------------------
2373 * Parse_File --
2374 *	Parse a file into its component parts, incorporating it into the
2375 *	current dependency graph. This is the main function and controls
2376 *	almost every other function in this module
2377 *
2378 * Results:
2379 *	None
2380 *
2381 * Side Effects:
2382 *	Loads. Nodes are added to the list of all targets, nodes and links
2383 *	are added to the dependency graph. etc. etc. etc.
2384 *---------------------------------------------------------------------
2385 */
2386void
2387Parse_File(const char *name, FILE *stream)
2388{
2389	char	*cp;	/* pointer into the line */
2390	char	*line;	/* the line we're working on */
2391
2392	inLine = FALSE;
2393	fatals = 0;
2394
2395	ParsePushInput(estrdup(name), stream, NULL, 0);
2396
2397	while ((line = ParseReadLine()) != NULL) {
2398		if (*line == '.' && parse_directive(line + 1)) {
2399			/* directive consumed */
2400			goto nextLine;
2401		}
2402		if (skipLine || *line == '#') {
2403			/* Skipping .if block or comment. */
2404			goto nextLine;
2405		}
2406
2407		if (*line == '\t') {
2408			/*
2409			 * If a line starts with a tab, it can only
2410			 * hope to be a creation command.
2411			 */
2412			for (cp = line + 1; isspace((unsigned char)*cp); cp++) {
2413				continue;
2414			}
2415			if (*cp) {
2416				if (inLine) {
2417					LstNode	*ln;
2418					GNode	*gn;
2419
2420					/*
2421					 * So long as it's not a blank
2422					 * line and we're actually in a
2423					 * dependency spec, add the
2424					 * command to the list of
2425					 * commands of all targets in
2426					 * the dependency spec.
2427					 */
2428					LST_FOREACH(ln, &targets) {
2429						gn = Lst_Datum(ln);
2430
2431						/*
2432						 * if target already
2433						 * supplied, ignore
2434						 * commands
2435						 */
2436						if (!(gn->type & OP_HAS_COMMANDS))
2437							Lst_AtEnd(&gn->commands, cp);
2438						else
2439							Parse_Error(PARSE_WARNING, "duplicate script "
2440							    "for target \"%s\" ignored", gn->name);
2441					}
2442					continue;
2443				} else {
2444					Parse_Error(PARSE_FATAL,
2445					     "Unassociated shell command \"%s\"",
2446					     cp);
2447				}
2448			}
2449#ifdef SYSVINCLUDE
2450		} else if (strncmp(line, "include", 7) == 0 &&
2451		    isspace((unsigned char)line[7]) &&
2452		    strchr(line, ':') == NULL) {
2453			/*
2454			 * It's an S3/S5-style "include".
2455			 */
2456			ParseTraditionalInclude(line + 7);
2457			goto nextLine;
2458#endif
2459		} else if (Parse_IsVar(line)) {
2460			ParseFinishLine();
2461			Parse_DoVar(line, VAR_GLOBAL);
2462
2463		} else {
2464			/*
2465			 * We now know it's a dependency line so it
2466			 * needs to have all variables expanded before
2467			 * being parsed. Tell the variable module to
2468			 * complain if some variable is undefined...
2469			 * To make life easier on novices, if the line
2470			 * is indented we first make sure the line has
2471			 * a dependency operator in it. If it doesn't
2472			 * have an operator and we're in a dependency
2473			 * line's script, we assume it's actually a
2474			 * shell command and add it to the current
2475			 * list of targets. XXX this comment seems wrong.
2476			 */
2477			cp = line;
2478			if (isspace((unsigned char)line[0])) {
2479				while (*cp != '\0' &&
2480				    isspace((unsigned char)*cp)) {
2481					cp++;
2482				}
2483				if (*cp == '\0') {
2484					goto nextLine;
2485				}
2486			}
2487
2488			ParseFinishLine();
2489
2490			cp = Buf_Peel(Var_Subst(line, VAR_CMD, TRUE));
2491
2492			free(line);
2493			line = cp;
2494
2495			/*
2496			 * Need a non-circular list for the target nodes
2497			 */
2498			Lst_Destroy(&targets, NOFREE);
2499			inLine = TRUE;
2500
2501			ParseDoDependency(line);
2502		}
2503
2504  nextLine:
2505		free(line);
2506	}
2507
2508	ParseFinishLine();
2509
2510	/*
2511	 * Make sure conditionals are clean
2512	 */
2513	Cond_End();
2514
2515	if (fatals)
2516		errx(1, "fatal errors encountered -- cannot continue");
2517}
2518
2519/*-
2520 *-----------------------------------------------------------------------
2521 * Parse_MainName --
2522 *	Return a Lst of the main target to create for main()'s sake. If
2523 *	no such target exists, we Punt with an obnoxious error message.
2524 *
2525 * Results:
2526 *	A Lst of the single node to create.
2527 *
2528 * Side Effects:
2529 *	None.
2530 *
2531 *-----------------------------------------------------------------------
2532 */
2533void
2534Parse_MainName(Lst *listmain)
2535{
2536
2537	if (mainNode == NULL) {
2538		Punt("no target to make.");
2539		/*NOTREACHED*/
2540	} else if (mainNode->type & OP_DOUBLEDEP) {
2541		Lst_AtEnd(listmain, mainNode);
2542		Lst_Concat(listmain, &mainNode->cohorts, LST_CONCNEW);
2543	} else
2544		Lst_AtEnd(listmain, mainNode);
2545}
2546