1/*	$NetBSD: parse.c,v 1.730 2024/06/02 15:31:26 rillig Exp $	*/
2
3/*
4 * Copyright (c) 1988, 1989, 1990, 1993
5 *	The Regents of the University of California.  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. Neither the name of the University nor the names of its contributors
19 *    may be used to endorse or promote products derived from this software
20 *    without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 * SUCH DAMAGE.
33 */
34
35/*
36 * Copyright (c) 1989 by Berkeley Softworks
37 * All rights reserved.
38 *
39 * This code is derived from software contributed to Berkeley by
40 * Adam de Boor.
41 *
42 * Redistribution and use in source and binary forms, with or without
43 * modification, are permitted provided that the following conditions
44 * are met:
45 * 1. Redistributions of source code must retain the above copyright
46 *    notice, this list of conditions and the following disclaimer.
47 * 2. Redistributions in binary form must reproduce the above copyright
48 *    notice, this list of conditions and the following disclaimer in the
49 *    documentation and/or other materials provided with the distribution.
50 * 3. All advertising materials mentioning features or use of this software
51 *    must display the following acknowledgement:
52 *	This product includes software developed by the University of
53 *	California, Berkeley and its contributors.
54 * 4. Neither the name of the University nor the names of its contributors
55 *    may be used to endorse or promote products derived from this software
56 *    without specific prior written permission.
57 *
58 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
59 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
60 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
61 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
62 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
63 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
64 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
65 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
66 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
67 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
68 * SUCH DAMAGE.
69 */
70
71/*
72 * Parsing of makefiles.
73 *
74 * Parse_File is the main entry point and controls most of the other
75 * functions in this module.
76 *
77 * Interface:
78 *	Parse_Init	Initialize the module
79 *
80 *	Parse_End	Clean up the module
81 *
82 *	Parse_File	Parse a top-level makefile.  Included files are
83 *			handled by IncludeFile instead.
84 *
85 *	Parse_VarAssign
86 *			Try to parse the given line as a variable assignment.
87 *			Used by MainParseArgs to determine if an argument is
88 *			a target or a variable assignment.  Used internally
89 *			for pretty much the same thing.
90 *
91 *	Parse_Error	Report a parse error, a warning or an informational
92 *			message.
93 *
94 *	Parse_MainName	Populate the list of targets to create.
95 */
96
97#include <sys/types.h>
98#include <sys/stat.h>
99#include <errno.h>
100#include <stdarg.h>
101
102#include "make.h"
103#include "dir.h"
104#include "job.h"
105#include "pathnames.h"
106
107/*	"@(#)parse.c	8.3 (Berkeley) 3/19/94"	*/
108MAKE_RCSID("$NetBSD: parse.c,v 1.730 2024/06/02 15:31:26 rillig Exp $");
109
110/* Detects a multiple-inclusion guard in a makefile. */
111typedef enum {
112	GS_START,		/* at the beginning of the file */
113	GS_COND,		/* after the guard condition */
114	GS_DONE,		/* after the closing .endif */
115	GS_NO			/* the file is not guarded */
116} GuardState;
117
118/* A file being parsed. */
119typedef struct IncludedFile {
120	FStr name;		/* absolute or relative to the cwd */
121	unsigned lineno;	/* 1-based */
122	unsigned readLines;	/* the number of physical lines that have
123				 * been read from the file */
124	unsigned forHeadLineno;	/* 1-based */
125	unsigned forBodyReadLines; /* the number of physical lines that have
126				 * been read from the file above the body of
127				 * the .for loop */
128	unsigned int condMinDepth; /* depth of nested 'if' directives, at the
129				 * beginning of the file */
130	bool depending;		/* state of doing_depend on EOF */
131
132	Buffer buf;		/* the file's content or the body of the .for
133				 * loop; either empty or ends with '\n' */
134	char *buf_ptr;		/* next char to be read from buf */
135	char *buf_end;		/* buf_end[-1] == '\n' */
136
137	GuardState guardState;
138	Guard *guard;
139
140	struct ForLoop *forLoop;
141} IncludedFile;
142
143/* Special attributes for target nodes. */
144typedef enum ParseSpecial {
145	SP_ATTRIBUTE,	/* Generic attribute */
146	SP_BEGIN,	/* .BEGIN */
147	SP_DEFAULT,	/* .DEFAULT */
148	SP_DELETE_ON_ERROR, /* .DELETE_ON_ERROR */
149	SP_END,		/* .END */
150	SP_ERROR,	/* .ERROR */
151	SP_IGNORE,	/* .IGNORE */
152	SP_INCLUDES,	/* .INCLUDES; not mentioned in the manual page */
153	SP_INTERRUPT,	/* .INTERRUPT */
154	SP_LIBS,	/* .LIBS; not mentioned in the manual page */
155	SP_MAIN,	/* .MAIN and no user-specified targets to make */
156	SP_META,	/* .META */
157	SP_MFLAGS,	/* .MFLAGS or .MAKEFLAGS */
158	SP_NOMETA,	/* .NOMETA */
159	SP_NOMETA_CMP,	/* .NOMETA_CMP */
160	SP_NOPATH,	/* .NOPATH */
161	SP_NOREADONLY,	/* .NOREADONLY */
162	SP_NOT,		/* Not special */
163	SP_NOTPARALLEL,	/* .NOTPARALLEL or .NO_PARALLEL */
164	SP_NULL,	/* .NULL; not mentioned in the manual page */
165	SP_OBJDIR,	/* .OBJDIR */
166	SP_ORDER,	/* .ORDER */
167	SP_PARALLEL,	/* .PARALLEL; not mentioned in the manual page */
168	SP_PATH,	/* .PATH or .PATH.suffix */
169	SP_PHONY,	/* .PHONY */
170	SP_POSIX,	/* .POSIX; not mentioned in the manual page */
171	SP_PRECIOUS,	/* .PRECIOUS */
172	SP_READONLY,	/* .READONLY */
173	SP_SHELL,	/* .SHELL */
174	SP_SILENT,	/* .SILENT */
175	SP_SINGLESHELL,	/* .SINGLESHELL; not mentioned in the manual page */
176	SP_STALE,	/* .STALE */
177	SP_SUFFIXES,	/* .SUFFIXES */
178	SP_SYSPATH,	/* .SYSPATH */
179	SP_WAIT		/* .WAIT */
180} ParseSpecial;
181
182typedef List SearchPathList;
183typedef ListNode SearchPathListNode;
184
185
186typedef enum VarAssignOp {
187	VAR_NORMAL,		/* = */
188	VAR_APPEND,		/* += */
189	VAR_DEFAULT,		/* ?= */
190	VAR_SUBST,		/* := */
191	VAR_SHELL		/* != or :sh= */
192} VarAssignOp;
193
194typedef struct VarAssign {
195	char *varname;		/* unexpanded */
196	VarAssignOp op;
197	const char *value;	/* unexpanded */
198} VarAssign;
199
200static bool Parse_IsVar(const char *, VarAssign *);
201static void Parse_Var(VarAssign *, GNode *);
202
203/*
204 * The target to be made if no targets are specified in the command line.
205 * This is the first target defined in any of the makefiles.
206 */
207GNode *mainNode;
208
209/*
210 * During parsing, the targets from the left-hand side of the currently
211 * active dependency line, or NULL if the current line does not belong to a
212 * dependency line, for example because it is a variable assignment.
213 *
214 * See unit-tests/deptgt.mk, keyword "parse.c:targets".
215 */
216static GNodeList *targets;
217
218#ifdef CLEANUP
219/*
220 * All shell commands for all targets, in no particular order and possibly
221 * with duplicate values.  Kept in a separate list since the commands from
222 * .USE or .USEBEFORE nodes are shared with other GNodes, thereby giving up
223 * the easily understandable ownership over the allocated strings.
224 */
225static StringList targCmds = LST_INIT;
226#endif
227
228/*
229 * Predecessor node for handling .ORDER. Initialized to NULL when .ORDER
230 * is seen, then set to each successive source on the line.
231 */
232static GNode *order_pred;
233
234static int parseErrors;
235
236/*
237 * The include chain of makefiles.  At index 0 is the top-level makefile from
238 * the command line, followed by the included files or .for loops, up to and
239 * including the current file.
240 *
241 * See PrintStackTrace for how to interpret the data.
242 */
243static Vector /* of IncludedFile */ includes;
244
245SearchPath *parseIncPath;	/* directories for "..." includes */
246SearchPath *sysIncPath;		/* directories for <...> includes */
247SearchPath *defSysIncPath;	/* default for sysIncPath */
248
249/*
250 * The parseKeywords table is searched using binary search when deciding
251 * if a target or source is special.
252 */
253static const struct {
254	const char name[17];
255	ParseSpecial special;	/* when used as a target */
256	GNodeType targetAttr;	/* when used as a source */
257} parseKeywords[] = {
258    { ".BEGIN",		SP_BEGIN,	OP_NONE },
259    { ".DEFAULT",	SP_DEFAULT,	OP_NONE },
260    { ".DELETE_ON_ERROR", SP_DELETE_ON_ERROR, OP_NONE },
261    { ".END",		SP_END,		OP_NONE },
262    { ".ERROR",		SP_ERROR,	OP_NONE },
263    { ".EXEC",		SP_ATTRIBUTE,	OP_EXEC },
264    { ".IGNORE",	SP_IGNORE,	OP_IGNORE },
265    { ".INCLUDES",	SP_INCLUDES,	OP_NONE },
266    { ".INTERRUPT",	SP_INTERRUPT,	OP_NONE },
267    { ".INVISIBLE",	SP_ATTRIBUTE,	OP_INVISIBLE },
268    { ".JOIN",		SP_ATTRIBUTE,	OP_JOIN },
269    { ".LIBS",		SP_LIBS,	OP_NONE },
270    { ".MADE",		SP_ATTRIBUTE,	OP_MADE },
271    { ".MAIN",		SP_MAIN,	OP_NONE },
272    { ".MAKE",		SP_ATTRIBUTE,	OP_MAKE },
273    { ".MAKEFLAGS",	SP_MFLAGS,	OP_NONE },
274    { ".META",		SP_META,	OP_META },
275    { ".MFLAGS",	SP_MFLAGS,	OP_NONE },
276    { ".NOMETA",	SP_NOMETA,	OP_NOMETA },
277    { ".NOMETA_CMP",	SP_NOMETA_CMP,	OP_NOMETA_CMP },
278    { ".NOPATH",	SP_NOPATH,	OP_NOPATH },
279    { ".NOREADONLY",	SP_NOREADONLY,	OP_NONE },
280    { ".NOTMAIN",	SP_ATTRIBUTE,	OP_NOTMAIN },
281    { ".NOTPARALLEL",	SP_NOTPARALLEL,	OP_NONE },
282    { ".NO_PARALLEL",	SP_NOTPARALLEL,	OP_NONE },
283    { ".NULL",		SP_NULL,	OP_NONE },
284    { ".OBJDIR",	SP_OBJDIR,	OP_NONE },
285    { ".OPTIONAL",	SP_ATTRIBUTE,	OP_OPTIONAL },
286    { ".ORDER",		SP_ORDER,	OP_NONE },
287    { ".PARALLEL",	SP_PARALLEL,	OP_NONE },
288    { ".PATH",		SP_PATH,	OP_NONE },
289    { ".PHONY",		SP_PHONY,	OP_PHONY },
290    { ".POSIX",		SP_POSIX,	OP_NONE },
291    { ".PRECIOUS",	SP_PRECIOUS,	OP_PRECIOUS },
292    { ".READONLY",	SP_READONLY,	OP_NONE },
293    { ".RECURSIVE",	SP_ATTRIBUTE,	OP_MAKE },
294    { ".SHELL",		SP_SHELL,	OP_NONE },
295    { ".SILENT",	SP_SILENT,	OP_SILENT },
296    { ".SINGLESHELL",	SP_SINGLESHELL,	OP_NONE },
297    { ".STALE",		SP_STALE,	OP_NONE },
298    { ".SUFFIXES",	SP_SUFFIXES,	OP_NONE },
299    { ".SYSPATH",	SP_SYSPATH,	OP_NONE },
300    { ".USE",		SP_ATTRIBUTE,	OP_USE },
301    { ".USEBEFORE",	SP_ATTRIBUTE,	OP_USEBEFORE },
302    { ".WAIT",		SP_WAIT,	OP_NONE },
303};
304
305enum PosixState posix_state = PS_NOT_YET;
306
307static HashTable /* full file name -> Guard */ guards;
308
309
310static List *
311Lst_New(void)
312{
313	List *list = bmake_malloc(sizeof *list);
314	Lst_Init(list);
315	return list;
316}
317
318static void
319Lst_Free(List *list)
320{
321
322	Lst_Done(list);
323	free(list);
324}
325
326static IncludedFile *
327GetInclude(size_t i)
328{
329	assert(i < includes.len);
330	return Vector_Get(&includes, i);
331}
332
333/* The makefile or the body of a .for loop that is currently being read. */
334static IncludedFile *
335CurFile(void)
336{
337	return GetInclude(includes.len - 1);
338}
339
340unsigned int
341CurFile_CondMinDepth(void)
342{
343	return CurFile()->condMinDepth;
344}
345
346static Buffer
347LoadFile(const char *path, int fd)
348{
349	ssize_t n;
350	Buffer buf;
351	size_t bufSize;
352	struct stat st;
353
354	bufSize = fstat(fd, &st) == 0 && S_ISREG(st.st_mode) &&
355		  st.st_size > 0 && st.st_size < 1024 * 1024 * 1024
356	    ? (size_t)st.st_size : 1024;
357	Buf_InitSize(&buf, bufSize);
358
359	for (;;) {
360		if (buf.len == buf.cap) {
361			if (buf.cap >= 512 * 1024 * 1024) {
362				Error("%s: file too large", path);
363				exit(2); /* Not 1 so -q can distinguish error */
364			}
365			Buf_Expand(&buf);
366		}
367		assert(buf.len < buf.cap);
368		n = read(fd, buf.data + buf.len, buf.cap - buf.len);
369		if (n < 0) {
370			Error("%s: read error: %s", path, strerror(errno));
371			exit(2);	/* Not 1 so -q can distinguish error */
372		}
373		if (n == 0)
374			break;
375
376		buf.len += (size_t)n;
377	}
378	assert(buf.len <= buf.cap);
379
380	if (buf.len > 0 && !Buf_EndsWith(&buf, '\n'))
381		Buf_AddByte(&buf, '\n');
382
383	return buf;		/* may not be null-terminated */
384}
385
386/*
387 * Print the current chain of .include and .for directives.  In Parse_Fatal
388 * or other functions that already print the location, includingInnermost
389 * would be redundant, but in other cases like Error or Fatal it needs to be
390 * included.
391 */
392void
393PrintStackTrace(bool includingInnermost)
394{
395	const IncludedFile *entries;
396	size_t i, n;
397
398	n = includes.len;
399	if (n == 0)
400		return;
401
402	entries = GetInclude(0);
403	if (!includingInnermost && entries[n - 1].forLoop == NULL)
404		n--;		/* already in the diagnostic */
405
406	for (i = n; i-- > 0;) {
407		const IncludedFile *entry = entries + i;
408		const char *fname = entry->name.str;
409		char dirbuf[MAXPATHLEN + 1];
410
411		if (fname[0] != '/' && strcmp(fname, "(stdin)") != 0) {
412			const char *realPath = realpath(fname, dirbuf);
413			if (realPath != NULL)
414				fname = realPath;
415		}
416
417		if (entry->forLoop != NULL) {
418			char *details = ForLoop_Details(entry->forLoop);
419			debug_printf("\tin .for loop from %s:%u with %s\n",
420			    fname, entry->forHeadLineno, details);
421			free(details);
422		} else if (i + 1 < n && entries[i + 1].forLoop != NULL) {
423			/* entry->lineno is not a useful line number */
424		} else
425			debug_printf("\tin %s:%u\n", fname, entry->lineno);
426	}
427}
428
429/* Check if the current character is escaped on the current line. */
430static bool
431IsEscaped(const char *line, const char *p)
432{
433	bool escaped = false;
434	while (p > line && *--p == '\\')
435		escaped = !escaped;
436	return escaped;
437}
438
439/*
440 * Remember the location (filename and lineno) where the last command was
441 * added or where the node was mentioned in a .depend file.
442 */
443static void
444RememberLocation(GNode *gn)
445{
446	IncludedFile *curFile = CurFile();
447	gn->fname = Str_Intern(curFile->name.str);
448	gn->lineno = curFile->lineno;
449}
450
451/*
452 * Look in the table of keywords for one matching the given string.
453 * Return the index of the keyword, or -1 if it isn't there.
454 */
455static int
456FindKeyword(const char *str)
457{
458	int start = 0;
459	int end = sizeof parseKeywords / sizeof parseKeywords[0] - 1;
460
461	while (start <= end) {
462		int curr = start + (end - start) / 2;
463		int diff = strcmp(str, parseKeywords[curr].name);
464
465		if (diff == 0)
466			return curr;
467		if (diff < 0)
468			end = curr - 1;
469		else
470			start = curr + 1;
471	}
472
473	return -1;
474}
475
476void
477PrintLocation(FILE *f, bool useVars, const GNode *gn)
478{
479	char dirbuf[MAXPATHLEN + 1];
480	FStr dir, base;
481	const char *fname;
482	unsigned lineno;
483
484	if (gn != NULL) {
485		fname = gn->fname;
486		lineno = gn->lineno;
487	} else if (includes.len > 0) {
488		IncludedFile *curFile = CurFile();
489		fname = curFile->name.str;
490		lineno = curFile->lineno;
491	} else
492		return;
493
494	if (!useVars || fname[0] == '/' || strcmp(fname, "(stdin)") == 0) {
495		(void)fprintf(f, "\"%s\" line %u: ", fname, lineno);
496		return;
497	}
498
499	dir = Var_Value(SCOPE_GLOBAL, ".PARSEDIR");
500	if (dir.str == NULL)
501		dir.str = ".";
502	if (dir.str[0] != '/')
503		dir.str = realpath(dir.str, dirbuf);
504
505	base = Var_Value(SCOPE_GLOBAL, ".PARSEFILE");
506	if (base.str == NULL)
507		base.str = str_basename(fname);
508
509	(void)fprintf(f, "\"%s/%s\" line %u: ", dir.str, base.str, lineno);
510
511	FStr_Done(&base);
512	FStr_Done(&dir);
513}
514
515static void MAKE_ATTR_PRINTFLIKE(5, 0)
516ParseVErrorInternal(FILE *f, bool useVars, const GNode *gn,
517		    ParseErrorLevel level, const char *fmt, va_list ap)
518{
519	static bool fatal_warning_error_printed = false;
520
521	(void)fprintf(f, "%s: ", progname);
522
523	PrintLocation(f, useVars, gn);
524	fprintf(f, "%s", EvalStack_Details());
525	if (level == PARSE_WARNING)
526		(void)fprintf(f, "warning: ");
527	(void)vfprintf(f, fmt, ap);
528	(void)fprintf(f, "\n");
529	(void)fflush(f);
530
531	if (level == PARSE_FATAL)
532		parseErrors++;
533	if (level == PARSE_WARNING && opts.parseWarnFatal) {
534		if (!fatal_warning_error_printed) {
535			Error("parsing warnings being treated as errors");
536			fatal_warning_error_printed = true;
537		}
538		parseErrors++;
539	}
540
541	if (DEBUG(PARSE))
542		PrintStackTrace(false);
543}
544
545static void MAKE_ATTR_PRINTFLIKE(3, 4)
546ParseErrorInternal(const GNode *gn,
547		   ParseErrorLevel level, const char *fmt, ...)
548{
549	va_list ap;
550
551	(void)fflush(stdout);
552	va_start(ap, fmt);
553	ParseVErrorInternal(stderr, false, gn, level, fmt, ap);
554	va_end(ap);
555
556	if (opts.debug_file != stdout && opts.debug_file != stderr) {
557		va_start(ap, fmt);
558		ParseVErrorInternal(opts.debug_file, false, gn,
559		    level, fmt, ap);
560		va_end(ap);
561	}
562}
563
564/*
565 * Print a message, including location information.
566 *
567 * If the level is PARSE_FATAL, continue parsing until the end of the
568 * current top-level makefile, then exit (see Parse_File).
569 *
570 * Fmt is given without a trailing newline.
571 */
572void
573Parse_Error(ParseErrorLevel level, const char *fmt, ...)
574{
575	va_list ap;
576
577	(void)fflush(stdout);
578	va_start(ap, fmt);
579	ParseVErrorInternal(stderr, true, NULL, level, fmt, ap);
580	va_end(ap);
581
582	if (opts.debug_file != stdout && opts.debug_file != stderr) {
583		va_start(ap, fmt);
584		ParseVErrorInternal(opts.debug_file, true, NULL,
585		    level, fmt, ap);
586		va_end(ap);
587	}
588}
589
590
591/*
592 * Handle an .info, .warning or .error directive.  For an .error directive,
593 * exit immediately.
594 */
595static void
596HandleMessage(ParseErrorLevel level, const char *levelName, const char *umsg)
597{
598	char *xmsg;
599
600	if (umsg[0] == '\0') {
601		Parse_Error(PARSE_FATAL, "Missing argument for \".%s\"",
602		    levelName);
603		return;
604	}
605
606	xmsg = Var_Subst(umsg, SCOPE_CMDLINE, VARE_EVAL);
607	/* TODO: handle errors */
608
609	Parse_Error(level, "%s", xmsg);
610	free(xmsg);
611
612	if (level == PARSE_FATAL) {
613		PrintOnError(NULL, "\n");
614		exit(1);
615	}
616}
617
618/*
619 * Add the child to the parent's children, and for non-special targets, vice
620 * versa.
621 */
622static void
623LinkSource(GNode *pgn, GNode *cgn, bool isSpecial)
624{
625	if ((pgn->type & OP_DOUBLEDEP) && !Lst_IsEmpty(&pgn->cohorts))
626		pgn = pgn->cohorts.last->datum;
627
628	Lst_Append(&pgn->children, cgn);
629	pgn->unmade++;
630
631	/*
632	 * Special targets like .END do not need to be informed once the child
633	 * target has been made.
634	 */
635	if (!isSpecial)
636		Lst_Append(&cgn->parents, pgn);
637
638	if (DEBUG(PARSE)) {
639		debug_printf("Target \"%s\" depends on \"%s\"\n",
640		    pgn->name, cgn->name);
641		Targ_PrintNode(pgn, 0);
642		Targ_PrintNode(cgn, 0);
643	}
644}
645
646/* Add the node to each target from the current dependency group. */
647static void
648LinkToTargets(GNode *gn, bool isSpecial)
649{
650	GNodeListNode *ln;
651
652	for (ln = targets->first; ln != NULL; ln = ln->next)
653		LinkSource(ln->datum, gn, isSpecial);
654}
655
656static bool
657TryApplyDependencyOperator(GNode *gn, GNodeType op)
658{
659	/*
660	 * If the node occurred on the left-hand side of a dependency and the
661	 * operator also defines a dependency, they must match.
662	 */
663	if ((op & OP_OPMASK) && (gn->type & OP_OPMASK) &&
664	    ((op & OP_OPMASK) != (gn->type & OP_OPMASK))) {
665		Parse_Error(PARSE_FATAL, "Inconsistent operator for %s",
666		    gn->name);
667		return false;
668	}
669
670	if (op == OP_DOUBLEDEP && (gn->type & OP_OPMASK) == OP_DOUBLEDEP) {
671		/*
672		 * If the node was on the left-hand side of a '::' operator,
673		 * create a new node for the children and commands on this
674		 * dependency line, since each of these dependency groups has
675		 * its own attributes and commands, separate from the others.
676		 *
677		 * The new instance is placed on the 'cohorts' list of the
678		 * initial one (note the initial one is not on its own
679		 * cohorts list) and the new instance is linked to all
680		 * parents of the initial instance.
681		 */
682		GNode *cohort;
683
684		/*
685		 * Propagate copied bits to the initial node.  They'll be
686		 * propagated back to the rest of the cohorts later.
687		 */
688		gn->type |= op & (unsigned)~OP_OPMASK;
689
690		cohort = Targ_NewInternalNode(gn->name);
691		if (doing_depend)
692			RememberLocation(cohort);
693		/*
694		 * Make the cohort invisible to avoid duplicating it
695		 * into other variables. True, parents of this target won't
696		 * tend to do anything with their local variables, but better
697		 * safe than sorry.
698		 *
699		 * (I think this is pointless now, since the relevant list
700		 * traversals will no longer see this node anyway. -mycroft)
701		 */
702		cohort->type = op | OP_INVISIBLE;
703		Lst_Append(&gn->cohorts, cohort);
704		cohort->centurion = gn;
705		gn->unmade_cohorts++;
706		snprintf(cohort->cohort_num, sizeof cohort->cohort_num, "#%d",
707		    (unsigned int)gn->unmade_cohorts % 1000000);
708	} else {
709		gn->type |= op;	/* preserve any previous flags */
710	}
711
712	return true;
713}
714
715static void
716ApplyDependencyOperator(GNodeType op)
717{
718	GNodeListNode *ln;
719
720	for (ln = targets->first; ln != NULL; ln = ln->next)
721		if (!TryApplyDependencyOperator(ln->datum, op))
722			break;
723}
724
725/*
726 * Add a .WAIT node in the dependency list. After any dynamic dependencies
727 * (and filename globbing) have happened, it is given a dependency on each
728 * previous child, back until the previous .WAIT node. The next child won't
729 * be scheduled until the .WAIT node is built.
730 *
731 * Give each .WAIT node a unique name (mainly for diagnostics).
732 */
733static void
734ApplyDependencySourceWait(bool isSpecial)
735{
736	static unsigned wait_number = 0;
737	char name[6 + 10 + 1];
738	GNode *gn;
739
740	snprintf(name, sizeof name, ".WAIT_%u", ++wait_number);
741	gn = Targ_NewInternalNode(name);
742	if (doing_depend)
743		RememberLocation(gn);
744	gn->type = OP_WAIT | OP_PHONY | OP_DEPENDS | OP_NOTMAIN;
745	LinkToTargets(gn, isSpecial);
746}
747
748static bool
749ApplyDependencySourceKeyword(const char *src, ParseSpecial special)
750{
751	int keywd;
752	GNodeType targetAttr;
753
754	if (*src != '.' || !ch_isupper(src[1]))
755		return false;
756
757	keywd = FindKeyword(src);
758	if (keywd == -1)
759		return false;
760
761	targetAttr = parseKeywords[keywd].targetAttr;
762	if (targetAttr != OP_NONE) {
763		ApplyDependencyOperator(targetAttr);
764		return true;
765	}
766	if (parseKeywords[keywd].special == SP_WAIT) {
767		ApplyDependencySourceWait(special != SP_NOT);
768		return true;
769	}
770	return false;
771}
772
773/*
774 * In a line like ".MAIN: source1 source2", add all sources to the list of
775 * things to create, but only if the user didn't specify a target on the
776 * command line and .MAIN occurs for the first time.
777 *
778 * See HandleDependencyTargetSpecial, branch SP_MAIN.
779 * See unit-tests/cond-func-make-main.mk.
780 */
781static void
782ApplyDependencySourceMain(const char *src)
783{
784	Lst_Append(&opts.create, bmake_strdup(src));
785	/*
786	 * Add the name to the .TARGETS variable as well, so the user can
787	 * employ that, if desired.
788	 */
789	Global_Append(".TARGETS", src);
790}
791
792/*
793 * For the sources of a .ORDER target, create predecessor/successor links
794 * between the previous source and the current one.
795 */
796static void
797ApplyDependencySourceOrder(const char *src)
798{
799	GNode *gn;
800
801	gn = Targ_GetNode(src);
802	if (doing_depend)
803		RememberLocation(gn);
804	if (order_pred != NULL) {
805		Lst_Append(&order_pred->order_succ, gn);
806		Lst_Append(&gn->order_pred, order_pred);
807		if (DEBUG(PARSE)) {
808			debug_printf(
809			    "# .ORDER forces '%s' to be made before '%s'\n",
810			    order_pred->name, gn->name);
811			Targ_PrintNode(order_pred, 0);
812			Targ_PrintNode(gn, 0);
813		}
814	}
815	/* The current source now becomes the predecessor for the next one. */
816	order_pred = gn;
817}
818
819/* The source is not an attribute, so find/create a node for it. */
820static void
821ApplyDependencySourceOther(const char *src, GNodeType targetAttr,
822			   ParseSpecial special)
823{
824	GNode *gn;
825
826	gn = Targ_GetNode(src);
827	if (doing_depend)
828		RememberLocation(gn);
829	if (targetAttr != OP_NONE)
830		gn->type |= targetAttr;
831	else
832		LinkToTargets(gn, special != SP_NOT);
833}
834
835/*
836 * Given the name of a source in a dependency line, figure out if it is an
837 * attribute (such as .SILENT) and if so, apply it to all targets. Otherwise
838 * decide if there is some attribute which should be applied *to* the source
839 * because of some special target (such as .PHONY) and apply it if so.
840 * Otherwise, make the source a child of the targets.
841 */
842static void
843ApplyDependencySource(GNodeType targetAttr, const char *src,
844		      ParseSpecial special)
845{
846	if (ApplyDependencySourceKeyword(src, special))
847		return;
848
849	if (special == SP_MAIN)
850		ApplyDependencySourceMain(src);
851	else if (special == SP_ORDER)
852		ApplyDependencySourceOrder(src);
853	else
854		ApplyDependencySourceOther(src, targetAttr, special);
855}
856
857/*
858 * If we have yet to decide on a main target to make, in the absence of any
859 * user input, we want the first target on the first dependency line that is
860 * actually a real target (i.e. isn't a .USE or .EXEC rule) to be made.
861 */
862static void
863MaybeUpdateMainTarget(void)
864{
865	GNodeListNode *ln;
866
867	if (mainNode != NULL)
868		return;
869
870	for (ln = targets->first; ln != NULL; ln = ln->next) {
871		GNode *gn = ln->datum;
872		if (GNode_IsMainCandidate(gn)) {
873			DEBUG1(MAKE, "Setting main node to \"%s\"\n",
874			    gn->name);
875			mainNode = gn;
876			return;
877		}
878	}
879}
880
881static void
882InvalidLineType(const char *line, const char *unexpanded_line)
883{
884	if (unexpanded_line[0] == '.') {
885		const char *dirstart = unexpanded_line + 1;
886		const char *dirend;
887		cpp_skip_whitespace(&dirstart);
888		dirend = dirstart;
889		while (ch_isalnum(*dirend) || *dirend == '-')
890			dirend++;
891		Parse_Error(PARSE_FATAL, "Unknown directive \"%.*s\"",
892		    (int)(dirend - dirstart), dirstart);
893	} else if (strcmp(line, unexpanded_line) == 0)
894		Parse_Error(PARSE_FATAL, "Invalid line '%s'", line);
895	else
896		Parse_Error(PARSE_FATAL,
897		    "Invalid line '%s', expanded to '%s'",
898		    unexpanded_line, line);
899}
900
901static void
902ParseDependencyTargetWord(char **pp, const char *lstart)
903{
904	const char *p = *pp;
905
906	while (*p != '\0') {
907		if ((ch_isspace(*p) || *p == '!' || *p == ':' || *p == '(')
908		    && !IsEscaped(lstart, p))
909			break;
910
911		if (*p == '$') {
912			FStr val = Var_Parse(&p, SCOPE_CMDLINE, VARE_PARSE);
913			/* TODO: handle errors */
914			FStr_Done(&val);
915		} else
916			p++;
917	}
918
919	*pp += p - *pp;
920}
921
922/*
923 * Handle special targets like .PATH, .DEFAULT, .BEGIN, .ORDER.
924 *
925 * See the tests deptgt-*.mk.
926 */
927static void
928HandleDependencyTargetSpecial(const char *targetName,
929			      ParseSpecial *inout_special,
930			      SearchPathList **inout_paths)
931{
932	switch (*inout_special) {
933	case SP_PATH:
934		if (*inout_paths == NULL)
935			*inout_paths = Lst_New();
936		Lst_Append(*inout_paths, &dirSearchPath);
937		break;
938	case SP_SYSPATH:
939		if (*inout_paths == NULL)
940			*inout_paths = Lst_New();
941		Lst_Append(*inout_paths, sysIncPath);
942		break;
943	case SP_MAIN:
944		/*
945		 * Allow targets from the command line to override the
946		 * .MAIN node.
947		 */
948		if (!Lst_IsEmpty(&opts.create))
949			*inout_special = SP_NOT;
950		break;
951	case SP_BEGIN:
952	case SP_END:
953	case SP_STALE:
954	case SP_ERROR:
955	case SP_INTERRUPT: {
956		GNode *gn = Targ_GetNode(targetName);
957		if (doing_depend)
958			RememberLocation(gn);
959		gn->type |= OP_NOTMAIN | OP_SPECIAL;
960		Lst_Append(targets, gn);
961		break;
962	}
963	case SP_DEFAULT: {
964		/*
965		 * Need to create a node to hang commands on, but we don't
966		 * want it in the graph, nor do we want it to be the Main
967		 * Target. We claim the node is a transformation rule to make
968		 * life easier later, when we'll use Make_HandleUse to
969		 * actually apply the .DEFAULT commands.
970		 */
971		GNode *gn = GNode_New(".DEFAULT");
972		gn->type |= OP_NOTMAIN | OP_TRANSFORM;
973		Lst_Append(targets, gn);
974		defaultNode = gn;
975		break;
976	}
977	case SP_DELETE_ON_ERROR:
978		deleteOnError = true;
979		break;
980	case SP_NOTPARALLEL:
981		opts.maxJobs = 1;
982		break;
983	case SP_SINGLESHELL:
984		opts.compatMake = true;
985		break;
986	case SP_ORDER:
987		order_pred = NULL;
988		break;
989	default:
990		break;
991	}
992}
993
994static bool
995HandleDependencyTargetPath(const char *suffixName,
996			   SearchPathList **inout_paths)
997{
998	SearchPath *path;
999
1000	path = Suff_GetPath(suffixName);
1001	if (path == NULL) {
1002		Parse_Error(PARSE_FATAL,
1003		    "Suffix '%s' not defined (yet)", suffixName);
1004		return false;
1005	}
1006
1007	if (*inout_paths == NULL)
1008		*inout_paths = Lst_New();
1009	Lst_Append(*inout_paths, path);
1010
1011	return true;
1012}
1013
1014/* See if it's a special target and if so set inout_special to match it. */
1015static bool
1016HandleDependencyTarget(const char *targetName,
1017		       ParseSpecial *inout_special,
1018		       GNodeType *inout_targetAttr,
1019		       SearchPathList **inout_paths)
1020{
1021	int keywd;
1022
1023	if (!(targetName[0] == '.' && ch_isupper(targetName[1])))
1024		return true;
1025
1026	/*
1027	 * See if the target is a special target that must have it
1028	 * or its sources handled specially.
1029	 */
1030	keywd = FindKeyword(targetName);
1031	if (keywd != -1) {
1032		if (*inout_special == SP_PATH &&
1033		    parseKeywords[keywd].special != SP_PATH) {
1034			Parse_Error(PARSE_FATAL, "Mismatched special targets");
1035			return false;
1036		}
1037
1038		*inout_special = parseKeywords[keywd].special;
1039		*inout_targetAttr = parseKeywords[keywd].targetAttr;
1040
1041		HandleDependencyTargetSpecial(targetName, inout_special,
1042		    inout_paths);
1043
1044	} else if (strncmp(targetName, ".PATH", 5) == 0) {
1045		*inout_special = SP_PATH;
1046		if (!HandleDependencyTargetPath(targetName + 5, inout_paths))
1047			return false;
1048	}
1049	return true;
1050}
1051
1052static void
1053HandleSingleDependencyTargetMundane(const char *name)
1054{
1055	GNode *gn = Suff_IsTransform(name)
1056	    ? Suff_AddTransform(name)
1057	    : Targ_GetNode(name);
1058	if (doing_depend)
1059		RememberLocation(gn);
1060
1061	Lst_Append(targets, gn);
1062}
1063
1064static void
1065HandleDependencyTargetMundane(const char *targetName)
1066{
1067	if (Dir_HasWildcards(targetName)) {
1068		StringList targetNames = LST_INIT;
1069
1070		SearchPath *emptyPath = SearchPath_New();
1071		SearchPath_Expand(emptyPath, targetName, &targetNames);
1072		SearchPath_Free(emptyPath);
1073
1074		while (!Lst_IsEmpty(&targetNames)) {
1075			char *targName = Lst_Dequeue(&targetNames);
1076			HandleSingleDependencyTargetMundane(targName);
1077			free(targName);
1078		}
1079	} else
1080		HandleSingleDependencyTargetMundane(targetName);
1081}
1082
1083static void
1084SkipExtraTargets(char **pp, const char *lstart)
1085{
1086	bool warning = false;
1087	const char *p = *pp;
1088
1089	while (*p != '\0') {
1090		if (!IsEscaped(lstart, p) && (*p == '!' || *p == ':'))
1091			break;
1092		if (IsEscaped(lstart, p) || (*p != ' ' && *p != '\t'))
1093			warning = true;
1094		p++;
1095	}
1096	if (warning) {
1097		const char *start = *pp;
1098		cpp_skip_whitespace(&start);
1099		Parse_Error(PARSE_WARNING, "Extra target '%.*s' ignored",
1100		    (int)(p - start), start);
1101	}
1102
1103	*pp += p - *pp;
1104}
1105
1106static void
1107CheckSpecialMundaneMixture(ParseSpecial special)
1108{
1109	switch (special) {
1110	case SP_DEFAULT:
1111	case SP_STALE:
1112	case SP_BEGIN:
1113	case SP_END:
1114	case SP_ERROR:
1115	case SP_INTERRUPT:
1116		/*
1117		 * These create nodes on which to hang commands, so targets
1118		 * shouldn't be empty.
1119		 */
1120	case SP_NOT:
1121		/* Nothing special here -- targets may be empty. */
1122		break;
1123	default:
1124		Parse_Error(PARSE_WARNING,
1125		    "Special and mundane targets don't mix. "
1126		    "Mundane ones ignored");
1127		break;
1128	}
1129}
1130
1131/*
1132 * In a dependency line like 'targets: sources' or 'targets! sources', parse
1133 * the operator ':', '::' or '!' from between the targets and the sources.
1134 */
1135static GNodeType
1136ParseDependencyOp(char **pp)
1137{
1138	if (**pp == '!')
1139		return (*pp)++, OP_FORCE;
1140	if (**pp == ':' && (*pp)[1] == ':')
1141		return *pp += 2, OP_DOUBLEDEP;
1142	else if (**pp == ':')
1143		return (*pp)++, OP_DEPENDS;
1144	else
1145		return OP_NONE;
1146}
1147
1148static void
1149ClearPaths(ParseSpecial special, SearchPathList *paths)
1150{
1151	if (paths != NULL) {
1152		SearchPathListNode *ln;
1153		for (ln = paths->first; ln != NULL; ln = ln->next)
1154			SearchPath_Clear(ln->datum);
1155	}
1156	if (special == SP_SYSPATH)
1157		Dir_SetSYSPATH();
1158	else
1159		Dir_SetPATH();
1160}
1161
1162static char *
1163FindInDirOfIncludingFile(const char *file)
1164{
1165	char *fullname, *incdir, *slash, *newName;
1166	int i;
1167
1168	fullname = NULL;
1169	incdir = bmake_strdup(CurFile()->name.str);
1170	slash = strrchr(incdir, '/');
1171	if (slash != NULL) {
1172		*slash = '\0';
1173		/*
1174		 * Now do lexical processing of leading "../" on the
1175		 * filename.
1176		 */
1177		for (i = 0; strncmp(file + i, "../", 3) == 0; i += 3) {
1178			slash = strrchr(incdir + 1, '/');
1179			if (slash == NULL || strcmp(slash, "/..") == 0)
1180				break;
1181			*slash = '\0';
1182		}
1183		newName = str_concat3(incdir, "/", file + i);
1184		fullname = Dir_FindFile(newName, parseIncPath);
1185		if (fullname == NULL)
1186			fullname = Dir_FindFile(newName, &dirSearchPath);
1187		free(newName);
1188	}
1189	free(incdir);
1190	return fullname;
1191}
1192
1193static char *
1194FindInQuotPath(const char *file)
1195{
1196	const char *suff;
1197	SearchPath *suffPath;
1198	char *fullname;
1199
1200	fullname = FindInDirOfIncludingFile(file);
1201	if (fullname == NULL &&
1202	    (suff = strrchr(file, '.')) != NULL &&
1203	    (suffPath = Suff_GetPath(suff)) != NULL)
1204		fullname = Dir_FindFile(file, suffPath);
1205	if (fullname == NULL)
1206		fullname = Dir_FindFile(file, parseIncPath);
1207	if (fullname == NULL)
1208		fullname = Dir_FindFile(file, &dirSearchPath);
1209	return fullname;
1210}
1211
1212static bool
1213SkipGuarded(const char *fullname)
1214{
1215	Guard *guard = HashTable_FindValue(&guards, fullname);
1216	if (guard != NULL && guard->kind == GK_VARIABLE
1217	    && GNode_ValueDirect(SCOPE_GLOBAL, guard->name) != NULL)
1218		goto skip;
1219	if (guard != NULL && guard->kind == GK_TARGET
1220	    && Targ_FindNode(guard->name) != NULL)
1221		goto skip;
1222	return false;
1223
1224skip:
1225	DEBUG2(PARSE, "Skipping '%s' because '%s' is defined\n",
1226	    fullname, guard->name);
1227	return true;
1228}
1229
1230/*
1231 * Handle one of the .[-ds]include directives by remembering the current file
1232 * and pushing the included file on the stack.  After the included file has
1233 * finished, parsing continues with the including file; see Parse_PushInput
1234 * and ParseEOF.
1235 *
1236 * System includes are looked up in sysIncPath, any other includes are looked
1237 * up in the parsedir and then in the directories specified by the -I command
1238 * line options.
1239 */
1240static void
1241IncludeFile(const char *file, bool isSystem, bool depinc, bool silent)
1242{
1243	Buffer buf;
1244	char *fullname;		/* full pathname of file */
1245	int fd;
1246
1247	fullname = file[0] == '/' ? bmake_strdup(file) : NULL;
1248
1249	if (fullname == NULL && !isSystem)
1250		fullname = FindInQuotPath(file);
1251
1252	if (fullname == NULL) {
1253		SearchPath *path = Lst_IsEmpty(&sysIncPath->dirs)
1254		    ? defSysIncPath : sysIncPath;
1255		fullname = Dir_FindInclude(file, path);
1256	}
1257
1258	if (fullname == NULL) {
1259		if (!silent)
1260			Parse_Error(PARSE_FATAL, "Could not find %s", file);
1261		return;
1262	}
1263
1264	if (SkipGuarded(fullname))
1265		goto done;
1266
1267	if ((fd = open(fullname, O_RDONLY)) == -1) {
1268		if (!silent)
1269			Parse_Error(PARSE_FATAL, "Cannot open %s", fullname);
1270		goto done;
1271	}
1272
1273	buf = LoadFile(fullname, fd);
1274	(void)close(fd);
1275
1276	Parse_PushInput(fullname, 1, 0, buf, NULL);
1277	if (depinc)
1278		doing_depend = depinc;	/* only turn it on */
1279done:
1280	free(fullname);
1281}
1282
1283/* Handle a "dependency" line like '.SPECIAL:' without any sources. */
1284static void
1285HandleDependencySourcesEmpty(ParseSpecial special, SearchPathList *paths)
1286{
1287	switch (special) {
1288	case SP_SUFFIXES:
1289		Suff_ClearSuffixes();
1290		break;
1291	case SP_PRECIOUS:
1292		allPrecious = true;
1293		break;
1294	case SP_IGNORE:
1295		opts.ignoreErrors = true;
1296		break;
1297	case SP_SILENT:
1298		opts.silent = true;
1299		break;
1300	case SP_PATH:
1301	case SP_SYSPATH:
1302		ClearPaths(special, paths);
1303		break;
1304	case SP_POSIX:
1305		if (posix_state == PS_NOW_OR_NEVER) {
1306			/*
1307			 * With '-r', 'posix.mk' (if it exists)
1308			 * can effectively substitute for 'sys.mk',
1309			 * otherwise it is an extension.
1310			 */
1311			Global_Set("%POSIX", "1003.2");
1312			IncludeFile("posix.mk", true, false, true);
1313		}
1314		break;
1315	default:
1316		break;
1317	}
1318}
1319
1320static void
1321AddToPaths(const char *dir, SearchPathList *paths)
1322{
1323	if (paths != NULL) {
1324		SearchPathListNode *ln;
1325		for (ln = paths->first; ln != NULL; ln = ln->next)
1326			(void)SearchPath_Add(ln->datum, dir);
1327	}
1328}
1329
1330/*
1331 * If the target was one that doesn't take files as its sources but takes
1332 * something like suffixes, we take each space-separated word on the line as
1333 * a something and deal with it accordingly.
1334 */
1335static void
1336ParseDependencySourceSpecial(ParseSpecial special, const char *word,
1337			     SearchPathList *paths)
1338{
1339	switch (special) {
1340	case SP_SUFFIXES:
1341		Suff_AddSuffix(word);
1342		break;
1343	case SP_PATH:
1344	case SP_SYSPATH:
1345		AddToPaths(word, paths);
1346		break;
1347	case SP_INCLUDES:
1348		Suff_AddInclude(word);
1349		break;
1350	case SP_LIBS:
1351		Suff_AddLib(word);
1352		break;
1353	case SP_NOREADONLY:
1354		Var_ReadOnly(word, false);
1355		break;
1356	case SP_NULL:
1357		Suff_SetNull(word);
1358		break;
1359	case SP_OBJDIR:
1360		Main_SetObjdir(false, "%s", word);
1361		break;
1362	case SP_READONLY:
1363		Var_ReadOnly(word, true);
1364		break;
1365	default:
1366		break;
1367	}
1368}
1369
1370static bool
1371ApplyDependencyTarget(char *name, char *nameEnd, ParseSpecial *inout_special,
1372		      GNodeType *inout_targetAttr,
1373		      SearchPathList **inout_paths)
1374{
1375	char savedNameEnd = *nameEnd;
1376	*nameEnd = '\0';
1377
1378	if (!HandleDependencyTarget(name, inout_special,
1379	    inout_targetAttr, inout_paths))
1380		return false;
1381
1382	if (*inout_special == SP_NOT && *name != '\0')
1383		HandleDependencyTargetMundane(name);
1384	else if (*inout_special == SP_PATH && *name != '.' && *name != '\0')
1385		Parse_Error(PARSE_WARNING, "Extra target (%s) ignored", name);
1386
1387	*nameEnd = savedNameEnd;
1388	return true;
1389}
1390
1391static bool
1392ParseDependencyTargets(char **pp,
1393		       const char *lstart,
1394		       ParseSpecial *inout_special,
1395		       GNodeType *inout_targetAttr,
1396		       SearchPathList **inout_paths,
1397		       const char *unexpanded_line)
1398{
1399	char *p = *pp;
1400
1401	for (;;) {
1402		char *tgt = p;
1403
1404		ParseDependencyTargetWord(&p, lstart);
1405
1406		/*
1407		 * If the word is followed by a left parenthesis, it's the
1408		 * name of one or more files inside an archive.
1409		 */
1410		if (!IsEscaped(lstart, p) && *p == '(') {
1411			p = tgt;
1412			if (!Arch_ParseArchive(&p, targets, SCOPE_CMDLINE)) {
1413				Parse_Error(PARSE_FATAL,
1414				    "Error in archive specification: \"%s\"",
1415				    tgt);
1416				return false;
1417			}
1418			continue;
1419		}
1420
1421		if (*p == '\0') {
1422			InvalidLineType(lstart, unexpanded_line);
1423			return false;
1424		}
1425
1426		if (!ApplyDependencyTarget(tgt, p, inout_special,
1427		    inout_targetAttr, inout_paths))
1428			return false;
1429
1430		if (*inout_special != SP_NOT && *inout_special != SP_PATH)
1431			SkipExtraTargets(&p, lstart);
1432		else
1433			pp_skip_whitespace(&p);
1434
1435		if (*p == '\0')
1436			break;
1437		if ((*p == '!' || *p == ':') && !IsEscaped(lstart, p))
1438			break;
1439	}
1440
1441	*pp = p;
1442	return true;
1443}
1444
1445static void
1446ParseDependencySourcesSpecial(char *start,
1447			      ParseSpecial special, SearchPathList *paths)
1448{
1449
1450	while (*start != '\0') {
1451		char savedEnd;
1452		char *end = start;
1453		while (*end != '\0' && !ch_isspace(*end))
1454			end++;
1455		savedEnd = *end;
1456		*end = '\0';
1457		ParseDependencySourceSpecial(special, start, paths);
1458		*end = savedEnd;
1459		if (savedEnd != '\0')
1460			end++;
1461		pp_skip_whitespace(&end);
1462		start = end;
1463	}
1464}
1465
1466static void
1467LinkVarToTargets(VarAssign *var)
1468{
1469	GNodeListNode *ln;
1470
1471	for (ln = targets->first; ln != NULL; ln = ln->next)
1472		Parse_Var(var, ln->datum);
1473}
1474
1475static bool
1476ParseDependencySourcesMundane(char *start,
1477			      ParseSpecial special, GNodeType targetAttr)
1478{
1479	while (*start != '\0') {
1480		char *end = start;
1481		VarAssign var;
1482
1483		/*
1484		 * Check for local variable assignment,
1485		 * rest of the line is the value.
1486		 */
1487		if (Parse_IsVar(start, &var)) {
1488			bool targetVarsEnabled = GetBooleanExpr(
1489			    "${.MAKE.TARGET_LOCAL_VARIABLES}", true);
1490
1491			if (targetVarsEnabled)
1492				LinkVarToTargets(&var);
1493			free(var.varname);
1494			if (targetVarsEnabled)
1495				return true;
1496		}
1497
1498		/*
1499		 * The targets take real sources, so we must beware of archive
1500		 * specifications (i.e. things with left parentheses in them)
1501		 * and handle them accordingly.
1502		 */
1503		for (; *end != '\0' && !ch_isspace(*end); end++) {
1504			if (*end == '(' && end > start && end[-1] != '$') {
1505				/*
1506				 * Only stop for a left parenthesis if it
1507				 * isn't at the start of a word (that'll be
1508				 * for variable changes later) and isn't
1509				 * preceded by a dollar sign (a dynamic
1510				 * source).
1511				 */
1512				break;
1513			}
1514		}
1515
1516		if (*end == '(') {
1517			GNodeList sources = LST_INIT;
1518			if (!Arch_ParseArchive(&start, &sources,
1519			    SCOPE_CMDLINE)) {
1520				Parse_Error(PARSE_FATAL,
1521				    "Error in source archive spec \"%s\"",
1522				    start);
1523				return false;
1524			}
1525
1526			while (!Lst_IsEmpty(&sources)) {
1527				GNode *gn = Lst_Dequeue(&sources);
1528				ApplyDependencySource(targetAttr, gn->name,
1529				    special);
1530			}
1531			Lst_Done(&sources);
1532			end = start;
1533		} else {
1534			if (*end != '\0') {
1535				*end = '\0';
1536				end++;
1537			}
1538
1539			ApplyDependencySource(targetAttr, start, special);
1540		}
1541		pp_skip_whitespace(&end);
1542		start = end;
1543	}
1544	return true;
1545}
1546
1547/*
1548 * From a dependency line like 'targets: sources', parse the sources.
1549 *
1550 * See the tests depsrc-*.mk.
1551 */
1552static void
1553ParseDependencySources(char *p, GNodeType targetAttr,
1554		       ParseSpecial special, SearchPathList **inout_paths)
1555{
1556	if (*p == '\0') {
1557		HandleDependencySourcesEmpty(special, *inout_paths);
1558	} else if (special == SP_MFLAGS) {
1559		Main_ParseArgLine(p);
1560		return;
1561	} else if (special == SP_SHELL) {
1562		if (!Job_ParseShell(p)) {
1563			Parse_Error(PARSE_FATAL,
1564			    "improper shell specification");
1565			return;
1566		}
1567		return;
1568	} else if (special == SP_NOTPARALLEL || special == SP_SINGLESHELL ||
1569		   special == SP_DELETE_ON_ERROR) {
1570		return;
1571	}
1572
1573	switch (special) {
1574	case SP_INCLUDES:
1575	case SP_LIBS:
1576	case SP_NOREADONLY:
1577	case SP_NULL:
1578	case SP_OBJDIR:
1579	case SP_PATH:
1580	case SP_READONLY:
1581	case SP_SUFFIXES:
1582	case SP_SYSPATH:
1583		ParseDependencySourcesSpecial(p, special, *inout_paths);
1584		if (*inout_paths != NULL) {
1585			Lst_Free(*inout_paths);
1586			*inout_paths = NULL;
1587		}
1588		if (special == SP_PATH)
1589			Dir_SetPATH();
1590		if (special == SP_SYSPATH)
1591			Dir_SetSYSPATH();
1592		break;
1593	default:
1594		assert(*inout_paths == NULL);
1595		if (!ParseDependencySourcesMundane(p, special, targetAttr))
1596			return;
1597		break;
1598	}
1599
1600	MaybeUpdateMainTarget();
1601}
1602
1603/*
1604 * Parse a dependency line consisting of targets, followed by a dependency
1605 * operator, optionally followed by sources.
1606 *
1607 * The nodes of the sources are linked as children to the nodes of the
1608 * targets. Nodes are created as necessary.
1609 *
1610 * The operator is applied to each node in the global 'targets' list,
1611 * which is where the nodes found for the targets are kept.
1612 *
1613 * The sources are parsed in much the same way as the targets, except
1614 * that they are expanded using the wildcarding scheme of the C-Shell,
1615 * and a target is created for each expanded word. Each of the resulting
1616 * nodes is then linked to each of the targets as one of its children.
1617 *
1618 * Certain targets and sources such as .PHONY or .PRECIOUS are handled
1619 * specially, see ParseSpecial.
1620 *
1621 * Transformation rules such as '.c.o' are also handled here, see
1622 * Suff_AddTransform.
1623 *
1624 * Upon return, the value of expandedLine is unspecified.
1625 */
1626static void
1627ParseDependency(char *expandedLine, const char *unexpandedLine)
1628{
1629	char *p;
1630	SearchPathList *paths;	/* search paths to alter when parsing a list
1631				 * of .PATH targets */
1632	GNodeType targetAttr;	/* from special sources */
1633	ParseSpecial special;	/* in special targets, the children are
1634				 * linked as children of the parent but not
1635				 * vice versa */
1636	GNodeType op;
1637
1638	DEBUG1(PARSE, "ParseDependency(%s)\n", expandedLine);
1639	p = expandedLine;
1640	paths = NULL;
1641	targetAttr = OP_NONE;
1642	special = SP_NOT;
1643
1644	if (!ParseDependencyTargets(&p, expandedLine, &special, &targetAttr,
1645	    &paths, unexpandedLine))
1646		goto out;
1647
1648	if (!Lst_IsEmpty(targets))
1649		CheckSpecialMundaneMixture(special);
1650
1651	op = ParseDependencyOp(&p);
1652	if (op == OP_NONE) {
1653		InvalidLineType(expandedLine, unexpandedLine);
1654		goto out;
1655	}
1656	ApplyDependencyOperator(op);
1657
1658	pp_skip_whitespace(&p);
1659
1660	ParseDependencySources(p, targetAttr, special, &paths);
1661
1662out:
1663	if (paths != NULL)
1664		Lst_Free(paths);
1665}
1666
1667/*
1668 * Determine the assignment operator and adjust the end of the variable
1669 * name accordingly.
1670 */
1671static VarAssign
1672AdjustVarassignOp(const char *name, const char *nameEnd, const char *op,
1673		  const char *value)
1674{
1675	VarAssignOp type;
1676	VarAssign va;
1677
1678	if (op > name && op[-1] == '+') {
1679		op--;
1680		type = VAR_APPEND;
1681
1682	} else if (op > name && op[-1] == '?') {
1683		op--;
1684		type = VAR_DEFAULT;
1685
1686	} else if (op > name && op[-1] == ':') {
1687		op--;
1688		type = VAR_SUBST;
1689
1690	} else if (op > name && op[-1] == '!') {
1691		op--;
1692		type = VAR_SHELL;
1693
1694	} else {
1695		type = VAR_NORMAL;
1696		while (op > name && ch_isspace(op[-1]))
1697			op--;
1698
1699		if (op - name >= 3 && memcmp(op - 3, ":sh", 3) == 0) {
1700			op -= 3;
1701			type = VAR_SHELL;
1702		}
1703	}
1704
1705	va.varname = bmake_strsedup(name, nameEnd < op ? nameEnd : op);
1706	va.op = type;
1707	va.value = value;
1708	return va;
1709}
1710
1711/*
1712 * Parse a variable assignment, consisting of a single-word variable name,
1713 * optional whitespace, an assignment operator, optional whitespace and the
1714 * variable value.
1715 *
1716 * Note: There is a lexical ambiguity with assignment modifier characters
1717 * in variable names. This routine interprets the character before the =
1718 * as a modifier. Therefore, an assignment like
1719 *	C++=/usr/bin/CC
1720 * is interpreted as "C+ +=" instead of "C++ =".
1721 *
1722 * Used for both lines in a file and command line arguments.
1723 */
1724static bool
1725Parse_IsVar(const char *p, VarAssign *out_var)
1726{
1727	const char *nameStart, *nameEnd, *firstSpace, *eq;
1728	int level = 0;
1729
1730	cpp_skip_hspace(&p);	/* Skip to variable name */
1731
1732	/*
1733	 * During parsing, the '+' of the operator '+=' is initially parsed
1734	 * as part of the variable name.  It is later corrected, as is the
1735	 * ':sh' modifier. Of these two (nameEnd and eq), the earlier one
1736	 * determines the actual end of the variable name.
1737	 */
1738
1739	nameStart = p;
1740	firstSpace = NULL;
1741
1742	/* Scan for one of the assignment operators outside an expression. */
1743	while (*p != '\0') {
1744		char ch = *p++;
1745		if (ch == '(' || ch == '{') {
1746			level++;
1747			continue;
1748		}
1749		if (ch == ')' || ch == '}') {
1750			level--;
1751			continue;
1752		}
1753
1754		if (level != 0)
1755			continue;
1756
1757		if ((ch == ' ' || ch == '\t') && firstSpace == NULL)
1758			firstSpace = p - 1;
1759		while (ch == ' ' || ch == '\t')
1760			ch = *p++;
1761
1762		if (ch == '\0')
1763			return false;
1764		if (ch == ':' && p[0] == 's' && p[1] == 'h') {
1765			p += 2;
1766			continue;
1767		}
1768		if (ch == '=')
1769			eq = p - 1;
1770		else if (*p == '=' &&
1771		    (ch == '+' || ch == ':' || ch == '?' || ch == '!'))
1772			eq = p;
1773		else if (firstSpace != NULL)
1774			return false;
1775		else
1776			continue;
1777
1778		nameEnd = firstSpace != NULL ? firstSpace : eq;
1779		p = eq + 1;
1780		cpp_skip_whitespace(&p);
1781		*out_var = AdjustVarassignOp(nameStart, nameEnd, eq, p);
1782		return true;
1783	}
1784
1785	return false;
1786}
1787
1788/*
1789 * Check for syntax errors such as unclosed expressions or unknown modifiers.
1790 */
1791static void
1792VarCheckSyntax(VarAssignOp op, const char *uvalue, GNode *scope)
1793{
1794	if (opts.strict) {
1795		if (op != VAR_SUBST && strchr(uvalue, '$') != NULL) {
1796			char *parsedValue = Var_Subst(uvalue,
1797			    scope, VARE_PARSE);
1798			/* TODO: handle errors */
1799			free(parsedValue);
1800		}
1801	}
1802}
1803
1804/* Perform a variable assignment that uses the operator ':='. */
1805static void
1806VarAssign_EvalSubst(GNode *scope, const char *name, const char *uvalue,
1807		    FStr *out_avalue)
1808{
1809	char *evalue;
1810
1811	/*
1812	 * Make sure that we set the variable the first time to nothing
1813	 * so that it gets substituted.
1814	 *
1815	 * TODO: Add a test that demonstrates why this code is needed,
1816	 *  apart from making the debug log longer.
1817	 *
1818	 * XXX: The variable name is expanded up to 3 times.
1819	 */
1820	if (!Var_ExistsExpand(scope, name))
1821		Var_SetExpand(scope, name, "");
1822
1823	evalue = Var_Subst(uvalue, scope,
1824	    VARE_EVAL_KEEP_DOLLAR_AND_UNDEFINED);
1825	/* TODO: handle errors */
1826
1827	Var_SetExpand(scope, name, evalue);
1828
1829	*out_avalue = FStr_InitOwn(evalue);
1830}
1831
1832/* Perform a variable assignment that uses the operator '!='. */
1833static void
1834VarAssign_EvalShell(const char *name, const char *uvalue, GNode *scope,
1835		    FStr *out_avalue)
1836{
1837	FStr cmd;
1838	char *output, *error;
1839
1840	cmd = FStr_InitRefer(uvalue);
1841	Var_Expand(&cmd, SCOPE_CMDLINE, VARE_EVAL_DEFINED);
1842
1843	output = Cmd_Exec(cmd.str, &error);
1844	Var_SetExpand(scope, name, output);
1845	*out_avalue = FStr_InitOwn(output);
1846	if (error != NULL) {
1847		Parse_Error(PARSE_WARNING, "%s", error);
1848		free(error);
1849	}
1850
1851	FStr_Done(&cmd);
1852}
1853
1854/*
1855 * Perform a variable assignment.
1856 *
1857 * The actual value of the variable is returned in *out_true_avalue.
1858 * Especially for VAR_SUBST and VAR_SHELL this can differ from the literal
1859 * value.
1860 *
1861 * Return whether the assignment was actually performed, which is usually
1862 * the case.  It is only skipped if the operator is '?=' and the variable
1863 * already exists.
1864 */
1865static bool
1866VarAssign_Eval(const char *name, VarAssignOp op, const char *uvalue,
1867	       GNode *scope, FStr *out_true_avalue)
1868{
1869	FStr avalue = FStr_InitRefer(uvalue);
1870
1871	if (op == VAR_APPEND)
1872		Var_AppendExpand(scope, name, uvalue);
1873	else if (op == VAR_SUBST)
1874		VarAssign_EvalSubst(scope, name, uvalue, &avalue);
1875	else if (op == VAR_SHELL)
1876		VarAssign_EvalShell(name, uvalue, scope, &avalue);
1877	else {
1878		/* XXX: The variable name is expanded up to 2 times. */
1879		if (op == VAR_DEFAULT && Var_ExistsExpand(scope, name))
1880			return false;
1881
1882		/* Normal assignment -- just do it. */
1883		Var_SetExpand(scope, name, uvalue);
1884	}
1885
1886	*out_true_avalue = avalue;
1887	return true;
1888}
1889
1890static void
1891VarAssignSpecial(const char *name, const char *avalue)
1892{
1893	if (strcmp(name, ".MAKEOVERRIDES") == 0)
1894		Main_ExportMAKEFLAGS(false);	/* re-export MAKEFLAGS */
1895	else if (strcmp(name, ".CURDIR") == 0) {
1896		/*
1897		 * Someone is being (too?) clever...
1898		 * Let's pretend they know what they are doing and
1899		 * re-initialize the 'cur' CachedDir.
1900		 */
1901		Dir_InitCur(avalue);
1902		Dir_SetPATH();
1903	} else if (strcmp(name, ".MAKE.JOB.PREFIX") == 0)
1904		Job_SetPrefix();
1905	else if (strcmp(name, ".MAKE.EXPORTED") == 0)
1906		Var_ExportVars(avalue);
1907}
1908
1909/* Perform the variable assignment in the given scope. */
1910static void
1911Parse_Var(VarAssign *var, GNode *scope)
1912{
1913	FStr avalue;		/* actual value (maybe expanded) */
1914
1915	VarCheckSyntax(var->op, var->value, scope);
1916	if (VarAssign_Eval(var->varname, var->op, var->value, scope, &avalue)) {
1917		VarAssignSpecial(var->varname, avalue.str);
1918		FStr_Done(&avalue);
1919	}
1920}
1921
1922
1923/*
1924 * See if the command possibly calls a sub-make by using the
1925 * expressions ${.MAKE}, ${MAKE} or the plain word "make".
1926 */
1927static bool
1928MaybeSubMake(const char *cmd)
1929{
1930	const char *start;
1931
1932	for (start = cmd; *start != '\0'; start++) {
1933		const char *p = start;
1934		char endc;
1935
1936		/* XXX: What if progname != "make"? */
1937		if (strncmp(p, "make", 4) == 0)
1938			if (start == cmd || !ch_isalnum(p[-1]))
1939				if (!ch_isalnum(p[4]))
1940					return true;
1941
1942		if (*p != '$')
1943			continue;
1944		p++;
1945
1946		if (*p == '{')
1947			endc = '}';
1948		else if (*p == '(')
1949			endc = ')';
1950		else
1951			continue;
1952		p++;
1953
1954		if (*p == '.')	/* Accept either ${.MAKE} or ${MAKE}. */
1955			p++;
1956
1957		if (strncmp(p, "MAKE", 4) == 0 && p[4] == endc)
1958			return true;
1959	}
1960	return false;
1961}
1962
1963/* Append the command to the target node. */
1964static void
1965GNode_AddCommand(GNode *gn, char *cmd)
1966{
1967	if ((gn->type & OP_DOUBLEDEP) && gn->cohorts.last != NULL)
1968		gn = gn->cohorts.last->datum;
1969
1970	/* if target already supplied, ignore commands */
1971	if (!(gn->type & OP_HAS_COMMANDS)) {
1972		Lst_Append(&gn->commands, cmd);
1973		if (MaybeSubMake(cmd))
1974			gn->type |= OP_SUBMAKE;
1975		RememberLocation(gn);
1976	} else {
1977		Parse_Error(PARSE_WARNING,
1978		    "duplicate script for target \"%s\" ignored",
1979		    gn->name);
1980		ParseErrorInternal(gn, PARSE_WARNING,
1981		    "using previous script for \"%s\" defined here",
1982		    gn->name);
1983	}
1984}
1985
1986/*
1987 * Parse a directive like '.include' or '.-include'.
1988 *
1989 * .include "user-makefile.mk"
1990 * .include <system-makefile.mk>
1991 */
1992static void
1993ParseInclude(char *directive)
1994{
1995	char endc;		/* '>' or '"' */
1996	char *p;
1997	bool silent = directive[0] != 'i';
1998	FStr file;
1999
2000	p = directive + (silent ? 8 : 7);
2001	pp_skip_hspace(&p);
2002
2003	if (*p != '"' && *p != '<') {
2004		Parse_Error(PARSE_FATAL,
2005		    ".include filename must be delimited by '\"' or '<'");
2006		return;
2007	}
2008
2009	endc = *p++ == '<' ? '>' : '"';
2010	file = FStr_InitRefer(p);
2011
2012	while (*p != '\0' && *p != endc)
2013		p++;
2014
2015	if (*p != endc) {
2016		Parse_Error(PARSE_FATAL,
2017		    "Unclosed .include filename. '%c' expected", endc);
2018		return;
2019	}
2020
2021	*p = '\0';
2022
2023	Var_Expand(&file, SCOPE_CMDLINE, VARE_EVAL);
2024	IncludeFile(file.str, endc == '>', directive[0] == 'd', silent);
2025	FStr_Done(&file);
2026}
2027
2028/*
2029 * Split filename into dirname + basename, then assign these to the
2030 * given variables.
2031 */
2032static void
2033SetFilenameVars(const char *filename, const char *dirvar, const char *filevar)
2034{
2035	const char *slash, *basename;
2036	FStr dirname;
2037
2038	slash = strrchr(filename, '/');
2039	if (slash == NULL) {
2040		dirname = FStr_InitRefer(curdir);
2041		basename = filename;
2042	} else {
2043		dirname = FStr_InitOwn(bmake_strsedup(filename, slash));
2044		basename = slash + 1;
2045	}
2046
2047	Global_Set(dirvar, dirname.str);
2048	Global_Set(filevar, basename);
2049
2050	DEBUG4(PARSE, "SetFilenameVars: ${%s} = `%s' ${%s} = `%s'\n",
2051	    dirvar, dirname.str, filevar, basename);
2052	FStr_Done(&dirname);
2053}
2054
2055/*
2056 * Return the immediately including file.
2057 *
2058 * This is made complicated since the .for loop is implemented as a special
2059 * kind of .include; see For_Run.
2060 */
2061static const char *
2062GetActuallyIncludingFile(void)
2063{
2064	size_t i;
2065	const IncludedFile *incs = GetInclude(0);
2066
2067	for (i = includes.len; i >= 2; i--)
2068		if (incs[i - 1].forLoop == NULL)
2069			return incs[i - 2].name.str;
2070	return NULL;
2071}
2072
2073/* Set .PARSEDIR, .PARSEFILE, .INCLUDEDFROMDIR and .INCLUDEDFROMFILE. */
2074static void
2075SetParseFile(const char *filename)
2076{
2077	const char *including;
2078
2079	SetFilenameVars(filename, ".PARSEDIR", ".PARSEFILE");
2080
2081	including = GetActuallyIncludingFile();
2082	if (including != NULL) {
2083		SetFilenameVars(including,
2084		    ".INCLUDEDFROMDIR", ".INCLUDEDFROMFILE");
2085	} else {
2086		Global_Delete(".INCLUDEDFROMDIR");
2087		Global_Delete(".INCLUDEDFROMFILE");
2088	}
2089}
2090
2091static bool
2092StrContainsWord(const char *str, const char *word)
2093{
2094	size_t strLen = strlen(str);
2095	size_t wordLen = strlen(word);
2096	const char *p;
2097
2098	if (strLen < wordLen)
2099		return false;
2100
2101	for (p = str; p != NULL; p = strchr(p, ' ')) {
2102		if (*p == ' ')
2103			p++;
2104		if (p > str + strLen - wordLen)
2105			return false;
2106
2107		if (memcmp(p, word, wordLen) == 0 &&
2108		    (p[wordLen] == '\0' || p[wordLen] == ' '))
2109			return true;
2110	}
2111	return false;
2112}
2113
2114/*
2115 * XXX: Searching through a set of words with this linear search is
2116 * inefficient for variables that contain thousands of words.
2117 *
2118 * XXX: The paths in this list don't seem to be normalized in any way.
2119 */
2120static bool
2121VarContainsWord(const char *varname, const char *word)
2122{
2123	FStr val = Var_Value(SCOPE_GLOBAL, varname);
2124	bool found = val.str != NULL && StrContainsWord(val.str, word);
2125	FStr_Done(&val);
2126	return found;
2127}
2128
2129/*
2130 * Track the makefiles we read - so makefiles can set dependencies on them.
2131 * Avoid adding anything more than once.
2132 *
2133 * Time complexity: O(n) per call, in total O(n^2), where n is the number
2134 * of makefiles that have been loaded.
2135 */
2136static void
2137TrackInput(const char *name)
2138{
2139	if (!VarContainsWord(".MAKE.MAKEFILES", name))
2140		Global_Append(".MAKE.MAKEFILES", name);
2141}
2142
2143
2144/* Parse from the given buffer, later return to the current file. */
2145void
2146Parse_PushInput(const char *name, unsigned lineno, unsigned readLines,
2147		Buffer buf, struct ForLoop *forLoop)
2148{
2149	IncludedFile *curFile;
2150
2151	if (forLoop != NULL)
2152		name = CurFile()->name.str;
2153	else
2154		TrackInput(name);
2155
2156	DEBUG3(PARSE, "Parse_PushInput: %s %s, line %u\n",
2157	    forLoop != NULL ? ".for loop in": "file", name, lineno);
2158
2159	curFile = Vector_Push(&includes);
2160	curFile->name = FStr_InitOwn(bmake_strdup(name));
2161	curFile->lineno = lineno;
2162	curFile->readLines = readLines;
2163	curFile->forHeadLineno = lineno;
2164	curFile->forBodyReadLines = readLines;
2165	curFile->buf = buf;
2166	curFile->depending = doing_depend;	/* restore this on EOF */
2167	curFile->guardState = forLoop == NULL ? GS_START : GS_NO;
2168	curFile->guard = NULL;
2169	curFile->forLoop = forLoop;
2170
2171	if (forLoop != NULL && !For_NextIteration(forLoop, &curFile->buf))
2172		abort();	/* see For_Run */
2173
2174	curFile->buf_ptr = curFile->buf.data;
2175	curFile->buf_end = curFile->buf.data + curFile->buf.len;
2176	curFile->condMinDepth = cond_depth;
2177	SetParseFile(name);
2178}
2179
2180/* Check if the directive is an include directive. */
2181static bool
2182IsInclude(const char *dir, bool sysv)
2183{
2184	if (dir[0] == 's' || dir[0] == '-' || (dir[0] == 'd' && !sysv))
2185		dir++;
2186
2187	if (strncmp(dir, "include", 7) != 0)
2188		return false;
2189
2190	/* Space is not mandatory for BSD .include */
2191	return !sysv || ch_isspace(dir[7]);
2192}
2193
2194
2195/* Check if the line is a SYSV include directive. */
2196static bool
2197IsSysVInclude(const char *line)
2198{
2199	const char *p;
2200
2201	if (!IsInclude(line, true))
2202		return false;
2203
2204	/* Avoid interpreting a dependency line as an include */
2205	for (p = line; (p = strchr(p, ':')) != NULL;) {
2206
2207		/* end of line -> it's a dependency */
2208		if (*++p == '\0')
2209			return false;
2210
2211		/* '::' operator or ': ' -> it's a dependency */
2212		if (*p == ':' || ch_isspace(*p))
2213			return false;
2214	}
2215	return true;
2216}
2217
2218/* Push to another file.  The line points to the word "include". */
2219static void
2220ParseTraditionalInclude(char *line)
2221{
2222	char *p;		/* current position in file spec */
2223	bool done = false;
2224	bool silent = line[0] != 'i';
2225	char *file = line + (silent ? 8 : 7);
2226	char *all_files;
2227
2228	DEBUG1(PARSE, "ParseTraditionalInclude: %s\n", file);
2229
2230	pp_skip_whitespace(&file);
2231
2232	all_files = Var_Subst(file, SCOPE_CMDLINE, VARE_EVAL);
2233	/* TODO: handle errors */
2234
2235	for (file = all_files; !done; file = p + 1) {
2236		/* Skip to end of line or next whitespace */
2237		for (p = file; *p != '\0' && !ch_isspace(*p); p++)
2238			continue;
2239
2240		if (*p != '\0')
2241			*p = '\0';
2242		else
2243			done = true;
2244
2245		IncludeFile(file, false, false, silent);
2246	}
2247
2248	free(all_files);
2249}
2250
2251/* Parse "export <variable>=<value>", and actually export it. */
2252static void
2253ParseGmakeExport(char *line)
2254{
2255	char *variable = line + 6;
2256	char *value;
2257
2258	DEBUG1(PARSE, "ParseGmakeExport: %s\n", variable);
2259
2260	pp_skip_whitespace(&variable);
2261
2262	for (value = variable; *value != '\0' && *value != '='; value++)
2263		continue;
2264
2265	if (*value != '=') {
2266		Parse_Error(PARSE_FATAL,
2267		    "Variable/Value missing from \"export\"");
2268		return;
2269	}
2270	*value++ = '\0';	/* terminate variable */
2271
2272	/*
2273	 * Expand the value before putting it in the environment.
2274	 */
2275	value = Var_Subst(value, SCOPE_CMDLINE, VARE_EVAL);
2276	/* TODO: handle errors */
2277
2278	setenv(variable, value, 1);
2279	free(value);
2280}
2281
2282/*
2283 * When the end of the current file or .for loop is reached, continue reading
2284 * the previous file at the previous location.
2285 *
2286 * Results:
2287 *	true to continue parsing, i.e. it had only reached the end of an
2288 *	included file, false if the main file has been parsed completely.
2289 */
2290static bool
2291ParseEOF(void)
2292{
2293	IncludedFile *curFile = CurFile();
2294
2295	doing_depend = curFile->depending;
2296	if (curFile->forLoop != NULL &&
2297	    For_NextIteration(curFile->forLoop, &curFile->buf)) {
2298		curFile->buf_ptr = curFile->buf.data;
2299		curFile->buf_end = curFile->buf.data + curFile->buf.len;
2300		curFile->readLines = curFile->forBodyReadLines;
2301		return true;
2302	}
2303
2304	Cond_EndFile();
2305
2306	if (curFile->guardState == GS_DONE) {
2307		HashEntry *he = HashTable_CreateEntry(&guards,
2308		    curFile->name.str, NULL);
2309		if (he->value != NULL) {
2310			free(((Guard *)he->value)->name);
2311			free(he->value);
2312		}
2313		HashEntry_Set(he, curFile->guard);
2314	} else if (curFile->guard != NULL) {
2315		free(curFile->guard->name);
2316		free(curFile->guard);
2317	}
2318
2319	FStr_Done(&curFile->name);
2320	Buf_Done(&curFile->buf);
2321	if (curFile->forLoop != NULL)
2322		ForLoop_Free(curFile->forLoop);
2323	Vector_Pop(&includes);
2324
2325	if (includes.len == 0) {
2326		/* We've run out of input */
2327		Global_Delete(".PARSEDIR");
2328		Global_Delete(".PARSEFILE");
2329		Global_Delete(".INCLUDEDFROMDIR");
2330		Global_Delete(".INCLUDEDFROMFILE");
2331		return false;
2332	}
2333
2334	curFile = CurFile();
2335	DEBUG2(PARSE, "ParseEOF: returning to file %s, line %u\n",
2336	    curFile->name.str, curFile->readLines + 1);
2337
2338	SetParseFile(curFile->name.str);
2339	return true;
2340}
2341
2342typedef enum ParseRawLineResult {
2343	PRLR_LINE,
2344	PRLR_EOF,
2345	PRLR_ERROR
2346} ParseRawLineResult;
2347
2348/*
2349 * Parse until the end of a line, taking into account lines that end with
2350 * backslash-newline.  The resulting line goes from out_line to out_line_end;
2351 * the line is not null-terminated.
2352 */
2353static ParseRawLineResult
2354ParseRawLine(IncludedFile *curFile, char **out_line, char **out_line_end,
2355	     char **out_firstBackslash, char **out_commentLineEnd)
2356{
2357	char *line = curFile->buf_ptr;
2358	char *buf_end = curFile->buf_end;
2359	char *p = line;
2360	char *line_end = line;
2361	char *firstBackslash = NULL;
2362	char *commentLineEnd = NULL;
2363	ParseRawLineResult res = PRLR_LINE;
2364
2365	curFile->readLines++;
2366
2367	for (;;) {
2368		char ch;
2369
2370		if (p == buf_end) {
2371			res = PRLR_EOF;
2372			break;
2373		}
2374
2375		ch = *p;
2376		if (ch == '\0' || (ch == '\\' && p[1] == '\0')) {
2377			Parse_Error(PARSE_FATAL, "Zero byte read from file");
2378			exit(2);
2379		}
2380
2381		/* Treat next character after '\' as literal. */
2382		if (ch == '\\') {
2383			if (firstBackslash == NULL)
2384				firstBackslash = p;
2385			if (p[1] == '\n') {
2386				curFile->readLines++;
2387				if (p + 2 == buf_end) {
2388					line_end = p;
2389					*line_end = '\n';
2390					p += 2;
2391					continue;
2392				}
2393			}
2394			p += 2;
2395			line_end = p;
2396			assert(p <= buf_end);
2397			continue;
2398		}
2399
2400		/*
2401		 * Remember the first '#' for comment stripping, unless
2402		 * the previous char was '[', as in the modifier ':[#]'.
2403		 */
2404		if (ch == '#' && commentLineEnd == NULL &&
2405		    !(p > line && p[-1] == '['))
2406			commentLineEnd = line_end;
2407
2408		p++;
2409		if (ch == '\n')
2410			break;
2411
2412		/* We are not interested in trailing whitespace. */
2413		if (!ch_isspace(ch))
2414			line_end = p;
2415	}
2416
2417	curFile->buf_ptr = p;
2418	*out_line = line;
2419	*out_line_end = line_end;
2420	*out_firstBackslash = firstBackslash;
2421	*out_commentLineEnd = commentLineEnd;
2422	return res;
2423}
2424
2425/*
2426 * Beginning at start, unescape '\#' to '#' and replace backslash-newline
2427 * with a single space.
2428 */
2429static void
2430UnescapeBackslash(char *line, char *start)
2431{
2432	const char *src = start;
2433	char *dst = start;
2434	char *spaceStart = line;
2435
2436	for (;;) {
2437		char ch = *src++;
2438		if (ch != '\\') {
2439			if (ch == '\0')
2440				break;
2441			*dst++ = ch;
2442			continue;
2443		}
2444
2445		ch = *src++;
2446		if (ch == '\0') {
2447			/* Delete '\\' at the end of the buffer. */
2448			dst--;
2449			break;
2450		}
2451
2452		/* Delete '\\' from before '#' on non-command lines. */
2453		if (ch == '#' && line[0] != '\t')
2454			*dst++ = ch;
2455		else if (ch == '\n') {
2456			cpp_skip_hspace(&src);
2457			*dst++ = ' ';
2458		} else {
2459			/* Leave '\\' in the buffer for later. */
2460			*dst++ = '\\';
2461			*dst++ = ch;
2462			/* Keep an escaped ' ' at the line end. */
2463			spaceStart = dst;
2464		}
2465	}
2466
2467	/* Delete any trailing spaces - eg from empty continuations */
2468	while (dst > spaceStart && ch_isspace(dst[-1]))
2469		dst--;
2470	*dst = '\0';
2471}
2472
2473typedef enum LineKind {
2474	/*
2475	 * Return the next line that is neither empty nor a comment.
2476	 * Backslash line continuations are folded into a single space.
2477	 * A trailing comment, if any, is discarded.
2478	 */
2479	LK_NONEMPTY,
2480
2481	/*
2482	 * Return the next line, even if it is empty or a comment.
2483	 * Preserve backslash-newline to keep the line numbers correct.
2484	 *
2485	 * Used in .for loops to collect the body of the loop while waiting
2486	 * for the corresponding .endfor.
2487	 */
2488	LK_FOR_BODY,
2489
2490	/*
2491	 * Return the next line that starts with a dot.
2492	 * Backslash line continuations are folded into a single space.
2493	 * A trailing comment, if any, is discarded.
2494	 *
2495	 * Used in .if directives to skip over irrelevant branches while
2496	 * waiting for the corresponding .endif.
2497	 */
2498	LK_DOT
2499} LineKind;
2500
2501/*
2502 * Return the next "interesting" logical line from the current file.  The
2503 * returned string will be freed at the end of including the file.
2504 */
2505static char *
2506ReadLowLevelLine(LineKind kind)
2507{
2508	IncludedFile *curFile = CurFile();
2509	ParseRawLineResult res;
2510	char *line;
2511	char *line_end;
2512	char *firstBackslash;
2513	char *commentLineEnd;
2514
2515	for (;;) {
2516		curFile->lineno = curFile->readLines + 1;
2517		res = ParseRawLine(curFile,
2518		    &line, &line_end, &firstBackslash, &commentLineEnd);
2519		if (res == PRLR_ERROR)
2520			return NULL;
2521
2522		if (line == line_end || line == commentLineEnd) {
2523			if (res == PRLR_EOF)
2524				return NULL;
2525			if (kind != LK_FOR_BODY)
2526				continue;
2527		}
2528
2529		/* We now have a line of data */
2530		assert(ch_isspace(*line_end));
2531		*line_end = '\0';
2532
2533		if (kind == LK_FOR_BODY)
2534			return line;	/* Don't join the physical lines. */
2535
2536		if (kind == LK_DOT && line[0] != '.')
2537			continue;
2538		break;
2539	}
2540
2541	if (commentLineEnd != NULL && line[0] != '\t')
2542		*commentLineEnd = '\0';
2543	if (firstBackslash != NULL)
2544		UnescapeBackslash(line, firstBackslash);
2545	return line;
2546}
2547
2548static bool
2549SkipIrrelevantBranches(void)
2550{
2551	const char *line;
2552
2553	while ((line = ReadLowLevelLine(LK_DOT)) != NULL)
2554		if (Cond_EvalLine(line) == CR_TRUE)
2555			return true;
2556	return false;
2557}
2558
2559static bool
2560ParseForLoop(const char *line)
2561{
2562	int rval;
2563	unsigned forHeadLineno;
2564	unsigned bodyReadLines;
2565	int forLevel;
2566
2567	rval = For_Eval(line);
2568	if (rval == 0)
2569		return false;	/* Not a .for line */
2570	if (rval < 0)
2571		return true;	/* Syntax error - error printed, ignore line */
2572
2573	forHeadLineno = CurFile()->lineno;
2574	bodyReadLines = CurFile()->readLines;
2575
2576	/* Accumulate the loop body until the matching '.endfor'. */
2577	forLevel = 1;
2578	do {
2579		line = ReadLowLevelLine(LK_FOR_BODY);
2580		if (line == NULL) {
2581			Parse_Error(PARSE_FATAL,
2582			    "Unexpected end of file in .for loop");
2583			break;
2584		}
2585	} while (For_Accum(line, &forLevel));
2586
2587	For_Run(forHeadLineno, bodyReadLines);
2588	return true;
2589}
2590
2591/*
2592 * Read an entire line from the input file.
2593 *
2594 * Empty lines, .if and .for are handled by this function, while variable
2595 * assignments, other directives, dependency lines and shell commands are
2596 * handled by the caller.
2597 *
2598 * Return a line without trailing whitespace, or NULL for EOF.  The returned
2599 * string will be freed at the end of including the file.
2600 */
2601static char *
2602ReadHighLevelLine(void)
2603{
2604	char *line;
2605	CondResult condResult;
2606
2607	for (;;) {
2608		IncludedFile *curFile = CurFile();
2609		line = ReadLowLevelLine(LK_NONEMPTY);
2610		if (posix_state == PS_MAYBE_NEXT_LINE)
2611			posix_state = PS_NOW_OR_NEVER;
2612		else
2613			posix_state = PS_TOO_LATE;
2614		if (line == NULL)
2615			return NULL;
2616
2617		DEBUG2(PARSE, "Parsing line %u: %s\n", curFile->lineno, line);
2618		if (curFile->guardState != GS_NO
2619		    && ((curFile->guardState == GS_START && line[0] != '.')
2620			|| curFile->guardState == GS_DONE))
2621			curFile->guardState = GS_NO;
2622		if (line[0] != '.')
2623			return line;
2624
2625		condResult = Cond_EvalLine(line);
2626		if (curFile->guardState == GS_START) {
2627			Guard *guard;
2628			if (condResult != CR_ERROR
2629			    && (guard = Cond_ExtractGuard(line)) != NULL) {
2630				curFile->guardState = GS_COND;
2631				curFile->guard = guard;
2632			} else
2633				curFile->guardState = GS_NO;
2634		}
2635		switch (condResult) {
2636		case CR_FALSE:	/* May also mean a syntax error. */
2637			if (!SkipIrrelevantBranches())
2638				return NULL;
2639			continue;
2640		case CR_TRUE:
2641			continue;
2642		case CR_ERROR:	/* Not a conditional line */
2643			if (ParseForLoop(line))
2644				continue;
2645			break;
2646		}
2647		return line;
2648	}
2649}
2650
2651static void
2652FinishDependencyGroup(void)
2653{
2654	GNodeListNode *ln;
2655
2656	if (targets == NULL)
2657		return;
2658
2659	for (ln = targets->first; ln != NULL; ln = ln->next) {
2660		GNode *gn = ln->datum;
2661
2662		Suff_EndTransform(gn);
2663
2664		/*
2665		 * Mark the target as already having commands if it does, to
2666		 * keep from having shell commands on multiple dependency
2667		 * lines.
2668		 */
2669		if (!Lst_IsEmpty(&gn->commands))
2670			gn->type |= OP_HAS_COMMANDS;
2671	}
2672
2673	Lst_Free(targets);
2674	targets = NULL;
2675}
2676
2677#ifdef CLEANUP
2678void Parse_RegisterCommand(char *cmd)
2679{
2680	Lst_Append(&targCmds, cmd);
2681}
2682#endif
2683
2684/* Add the command to each target from the current dependency spec. */
2685static void
2686ParseLine_ShellCommand(const char *p)
2687{
2688	cpp_skip_whitespace(&p);
2689	if (*p == '\0')
2690		return;		/* skip empty commands */
2691
2692	if (targets == NULL) {
2693		Parse_Error(PARSE_FATAL,
2694		    "Unassociated shell command \"%s\"", p);
2695		return;
2696	}
2697
2698	{
2699		char *cmd = bmake_strdup(p);
2700		GNodeListNode *ln;
2701
2702		for (ln = targets->first; ln != NULL; ln = ln->next) {
2703			GNode *gn = ln->datum;
2704			GNode_AddCommand(gn, cmd);
2705		}
2706		Parse_RegisterCommand(cmd);
2707	}
2708}
2709
2710static void
2711HandleBreak(const char *arg)
2712{
2713	IncludedFile *curFile = CurFile();
2714
2715	if (arg[0] != '\0')
2716		Parse_Error(PARSE_FATAL,
2717		    "The .break directive does not take arguments");
2718
2719	if (curFile->forLoop != NULL) {
2720		/* pretend we reached EOF */
2721		For_Break(curFile->forLoop);
2722		cond_depth = CurFile_CondMinDepth();
2723		ParseEOF();
2724	} else
2725		Parse_Error(PARSE_FATAL, "break outside of for loop");
2726}
2727
2728/*
2729 * See if the line starts with one of the known directives, and if so, handle
2730 * the directive.
2731 */
2732static bool
2733ParseDirective(char *line)
2734{
2735	char *p = line + 1;
2736	const char *arg;
2737	Substring dir;
2738
2739	pp_skip_whitespace(&p);
2740	if (IsInclude(p, false)) {
2741		ParseInclude(p);
2742		return true;
2743	}
2744
2745	dir.start = p;
2746	while (ch_islower(*p) || *p == '-')
2747		p++;
2748	dir.end = p;
2749
2750	if (*p != '\0' && !ch_isspace(*p))
2751		return false;
2752
2753	pp_skip_whitespace(&p);
2754	arg = p;
2755
2756	if (Substring_Equals(dir, "break"))
2757		HandleBreak(arg);
2758	else if (Substring_Equals(dir, "undef"))
2759		Var_Undef(arg);
2760	else if (Substring_Equals(dir, "export"))
2761		Var_Export(VEM_PLAIN, arg);
2762	else if (Substring_Equals(dir, "export-all"))
2763		Var_Export(VEM_ALL, arg);
2764	else if (Substring_Equals(dir, "export-env"))
2765		Var_Export(VEM_ENV, arg);
2766	else if (Substring_Equals(dir, "export-literal"))
2767		Var_Export(VEM_LITERAL, arg);
2768	else if (Substring_Equals(dir, "unexport"))
2769		Var_UnExport(false, arg);
2770	else if (Substring_Equals(dir, "unexport-env"))
2771		Var_UnExport(true, arg);
2772	else if (Substring_Equals(dir, "info"))
2773		HandleMessage(PARSE_INFO, "info", arg);
2774	else if (Substring_Equals(dir, "warning"))
2775		HandleMessage(PARSE_WARNING, "warning", arg);
2776	else if (Substring_Equals(dir, "error"))
2777		HandleMessage(PARSE_FATAL, "error", arg);
2778	else
2779		return false;
2780	return true;
2781}
2782
2783bool
2784Parse_VarAssign(const char *line, bool finishDependencyGroup, GNode *scope)
2785{
2786	VarAssign var;
2787
2788	if (!Parse_IsVar(line, &var))
2789		return false;
2790	if (finishDependencyGroup)
2791		FinishDependencyGroup();
2792	Parse_Var(&var, scope);
2793	free(var.varname);
2794	return true;
2795}
2796
2797void
2798Parse_GuardElse(void)
2799{
2800	IncludedFile *curFile = CurFile();
2801	if (cond_depth == curFile->condMinDepth + 1)
2802		curFile->guardState = GS_NO;
2803}
2804
2805void
2806Parse_GuardEndif(void)
2807{
2808	IncludedFile *curFile = CurFile();
2809	if (cond_depth == curFile->condMinDepth
2810	    && curFile->guardState == GS_COND)
2811		curFile->guardState = GS_DONE;
2812}
2813
2814static char *
2815FindSemicolon(char *p)
2816{
2817	int depth = 0;
2818
2819	for (; *p != '\0'; p++) {
2820		if (*p == '\\' && p[1] != '\0') {
2821			p++;
2822			continue;
2823		}
2824
2825		if (*p == '$' && (p[1] == '(' || p[1] == '{'))
2826			depth++;
2827		else if (depth > 0 && (*p == ')' || *p == '}'))
2828			depth--;
2829		else if (depth == 0 && *p == ';')
2830			break;
2831	}
2832	return p;
2833}
2834
2835static void
2836ParseDependencyLine(char *line)
2837{
2838	VarEvalMode emode;
2839	char *expanded_line;
2840	const char *shellcmd = NULL;
2841
2842	{
2843		char *semicolon = FindSemicolon(line);
2844		if (*semicolon != '\0') {
2845			/* Terminate the dependency list at the ';' */
2846			*semicolon = '\0';
2847			shellcmd = semicolon + 1;
2848		}
2849	}
2850
2851	/*
2852	 * We now know it's a dependency line, so it needs to have all
2853	 * variables expanded before being parsed.
2854	 *
2855	 * XXX: Ideally the dependency line would first be split into
2856	 * its left-hand side, dependency operator and right-hand side,
2857	 * and then each side would be expanded on its own.  This would
2858	 * allow for the left-hand side to allow only defined variables
2859	 * and to allow variables on the right-hand side to be undefined
2860	 * as well.
2861	 *
2862	 * Parsing the line first would also prevent that targets
2863	 * generated from expressions are interpreted as the
2864	 * dependency operator, such as in "target${:U\:} middle: source",
2865	 * in which the middle is interpreted as a source, not a target.
2866	 */
2867
2868	/*
2869	 * In lint mode, allow undefined variables to appear in dependency
2870	 * lines.
2871	 *
2872	 * Ideally, only the right-hand side would allow undefined variables
2873	 * since it is common to have optional dependencies. Having undefined
2874	 * variables on the left-hand side is more unusual though.  Since
2875	 * both sides are expanded in a single pass, there is not much choice
2876	 * what to do here.
2877	 *
2878	 * In normal mode, it does not matter whether undefined variables are
2879	 * allowed or not since as of 2020-09-14, Var_Parse does not print
2880	 * any parse errors in such a case. It simply returns the special
2881	 * empty string var_Error, which cannot be detected in the result of
2882	 * Var_Subst.
2883	 */
2884	emode = opts.strict ? VARE_EVAL : VARE_EVAL_DEFINED;
2885	expanded_line = Var_Subst(line, SCOPE_CMDLINE, emode);
2886	/* TODO: handle errors */
2887
2888	/* Need a fresh list for the target nodes */
2889	if (targets != NULL)
2890		Lst_Free(targets);
2891	targets = Lst_New();
2892
2893	ParseDependency(expanded_line, line);
2894	free(expanded_line);
2895
2896	if (shellcmd != NULL)
2897		ParseLine_ShellCommand(shellcmd);
2898}
2899
2900static void
2901ParseLine(char *line)
2902{
2903	if (line[0] == '.' && ParseDirective(line))
2904		return;
2905
2906	if (line[0] == '\t') {
2907		ParseLine_ShellCommand(line + 1);
2908		return;
2909	}
2910
2911	if (IsSysVInclude(line)) {
2912		ParseTraditionalInclude(line);
2913		return;
2914	}
2915
2916	if (strncmp(line, "export", 6) == 0 && ch_isspace(line[6]) &&
2917	    strchr(line, ':') == NULL) {
2918		ParseGmakeExport(line);
2919		return;
2920	}
2921
2922	if (Parse_VarAssign(line, true, SCOPE_GLOBAL))
2923		return;
2924
2925	FinishDependencyGroup();
2926
2927	ParseDependencyLine(line);
2928}
2929
2930/* Interpret a top-level makefile. */
2931void
2932Parse_File(const char *name, int fd)
2933{
2934	char *line;
2935	Buffer buf;
2936
2937	buf = LoadFile(name, fd != -1 ? fd : STDIN_FILENO);
2938	if (fd != -1)
2939		(void)close(fd);
2940
2941	assert(targets == NULL);
2942
2943	Parse_PushInput(name, 1, 0, buf, NULL);
2944
2945	do {
2946		while ((line = ReadHighLevelLine()) != NULL) {
2947			ParseLine(line);
2948		}
2949	} while (ParseEOF());
2950
2951	FinishDependencyGroup();
2952
2953	if (parseErrors != 0) {
2954		(void)fflush(stdout);
2955		(void)fprintf(stderr,
2956		    "%s: Fatal errors encountered -- cannot continue\n",
2957		    progname);
2958		PrintOnError(NULL, "");
2959		exit(1);
2960	}
2961}
2962
2963/* Initialize the parsing module. */
2964void
2965Parse_Init(void)
2966{
2967	mainNode = NULL;
2968	parseIncPath = SearchPath_New();
2969	sysIncPath = SearchPath_New();
2970	defSysIncPath = SearchPath_New();
2971	Vector_Init(&includes, sizeof(IncludedFile));
2972	HashTable_Init(&guards);
2973}
2974
2975/* Clean up the parsing module. */
2976void
2977Parse_End(void)
2978{
2979#ifdef CLEANUP
2980	HashIter hi;
2981
2982	Lst_DoneFree(&targCmds);
2983	assert(targets == NULL);
2984	SearchPath_Free(defSysIncPath);
2985	SearchPath_Free(sysIncPath);
2986	SearchPath_Free(parseIncPath);
2987	assert(includes.len == 0);
2988	Vector_Done(&includes);
2989	HashIter_Init(&hi, &guards);
2990	while (HashIter_Next(&hi)) {
2991		Guard *guard = hi.entry->value;
2992		free(guard->name);
2993		free(guard);
2994	}
2995	HashTable_Done(&guards);
2996#endif
2997}
2998
2999
3000/* Populate the list with the single main target to create, or error out. */
3001void
3002Parse_MainName(GNodeList *mainList)
3003{
3004	if (mainNode == NULL)
3005		Punt("no target to make.");
3006
3007	Lst_Append(mainList, mainNode);
3008	if (mainNode->type & OP_DOUBLEDEP)
3009		Lst_AppendAll(mainList, &mainNode->cohorts);
3010
3011	Global_Append(".TARGETS", mainNode->name);
3012}
3013
3014int
3015Parse_NumErrors(void)
3016{
3017	return parseErrors;
3018}
3019