[BACK]Return to parse.c CVS log [TXT][DIR] Up to [cvs.NetBSD.org] / src / usr.bin / make

Annotation of src/usr.bin/make/parse.c, Revision 1.303

1.303   ! rillig      1: /*     $NetBSD: parse.c,v 1.302 2020/09/13 13:50:27 rillig Exp $       */
1.15      christos    2:
1.1       cgd         3: /*
1.27      christos    4:  * Copyright (c) 1988, 1989, 1990, 1993
                      5:  *     The Regents of the University of California.  All rights reserved.
1.94      agc         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: /*
1.1       cgd        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:  * parse.c --
                     73:  *     Functions to parse a makefile.
                     74:  *
                     75:  *     One function, Parse_Init, must be called before any functions
                     76:  *     in this module are used. After that, the function Parse_File is the
                     77:  *     main entry point and controls most of the other functions in this
                     78:  *     module.
                     79:  *
                     80:  *     Most important structures are kept in Lsts. Directories for
1.123     dsl        81:  *     the .include "..." function are kept in the 'parseIncPath' Lst, while
                     82:  *     those for the .include <...> are kept in the 'sysIncPath' Lst. The
1.1       cgd        83:  *     targets currently being defined are kept in the 'targets' Lst.
                     84:  *
                     85:  *     The variables 'fname' and 'lineno' are used to track the name
                     86:  *     of the current file and the line number in that file so that error
                     87:  *     messages can be more meaningful.
                     88:  *
                     89:  * Interface:
                     90:  *     Parse_Init                  Initialization function which must be
                     91:  *                                 called before anything else in this module
                     92:  *                                 is used.
                     93:  *
1.9       jtc        94:  *     Parse_End                   Cleanup the module
                     95:  *
1.1       cgd        96:  *     Parse_File                  Function used to parse a makefile. It must
                     97:  *                                 be given the name of the file, which should
                     98:  *                                 already have been opened, and a function
                     99:  *                                 to call to read a character from the file.
                    100:  *
                    101:  *     Parse_IsVar                 Returns TRUE if the given line is a
                    102:  *                                 variable assignment. Used by MainParseArgs
                    103:  *                                 to determine if an argument is a target
                    104:  *                                 or a variable assignment. Used internally
                    105:  *                                 for pretty much the same thing...
                    106:  *
                    107:  *     Parse_Error                 Function called when an error occurs in
                    108:  *                                 parsing. Used by the variable and
                    109:  *                                 conditional modules.
                    110:  *     Parse_MainName              Returns a Lst of the main target to create.
                    111:  */
                    112:
1.170     dholland  113: #include <sys/types.h>
                    114: #include <sys/mman.h>
1.171     dholland  115: #include <sys/stat.h>
1.84      wiz       116: #include <errno.h>
1.5       cgd       117: #include <stdarg.h>
                    118: #include <stdio.h>
1.225     maya      119: #include <stdint.h>
1.84      wiz       120:
1.177     nakayama  121: #ifndef MAP_FILE
                    122: #define MAP_FILE 0
                    123: #endif
1.170     dholland  124: #ifndef MAP_COPY
                    125: #define MAP_COPY MAP_PRIVATE
                    126: #endif
                    127:
1.1       cgd       128: #include "make.h"
1.5       cgd       129: #include "dir.h"
                    130: #include "job.h"
1.1       cgd       131: #include "pathnames.h"
                    132:
1.303   ! rillig    133: /*     "@(#)parse.c    8.3 (Berkeley) 3/19/94" */
        !           134: MAKE_RCSID("$NetBSD: parse.c,v 1.302 2020/09/13 13:50:27 rillig Exp $");
        !           135:
1.248     rillig    136: /* types and constants */
1.166     dholland  137:
1.1       cgd       138: /*
1.166     dholland  139:  * Structure for a file being read ("included file")
1.1       cgd       140:  */
                    141: typedef struct IFile {
1.189     sjg       142:     char           *fname;         /* name of file */
1.281     rillig    143:     Boolean         fromForLoop;    /* simulated .include by the .for loop */
1.155     dsl       144:     int             lineno;         /* current line number in file */
                    145:     int             first_lineno;   /* line number of start of text */
                    146:     int             cond_depth;     /* 'if' nesting when file opened */
1.210     sjg       147:     Boolean         depending;      /* state of doing_depend on EOF */
1.123     dsl       148:     char            *P_str;         /* point to base of string buffer */
                    149:     char            *P_ptr;         /* point to next char of string buffer */
1.125     dsl       150:     char            *P_end;         /* point to the end of string buffer */
1.170     dholland  151:     char            *(*nextbuf)(void *, size_t *); /* Function to get more data */
1.155     dsl       152:     void            *nextbuf_arg;   /* Opaque arg for nextbuf() */
1.170     dholland  153:     struct loadedfile *lf;          /* loadedfile object, if any */
1.5       cgd       154: } IFile;
1.1       cgd       155:
1.82      reinoud   156:
                    157: /*
1.166     dholland  158:  * These values are returned by ParseEOF to tell Parse_File whether to
                    159:  * CONTINUE parsing, i.e. it had only reached the end of an include file,
                    160:  * or if it's DONE.
1.82      reinoud   161:  */
1.166     dholland  162: #define CONTINUE       1
                    163: #define DONE           0
1.82      reinoud   164:
1.166     dholland  165: /*
                    166:  * Tokens for target attributes
1.1       cgd       167:  */
                    168: typedef enum {
                    169:     Begin,         /* .BEGIN */
                    170:     Default,       /* .DEFAULT */
1.215     dholland  171:     DeleteOnError,  /* .DELETE_ON_ERROR */
1.1       cgd       172:     End,           /* .END */
1.162     sjg       173:     dotError,      /* .ERROR */
1.1       cgd       174:     Ignore,        /* .IGNORE */
                    175:     Includes,      /* .INCLUDES */
                    176:     Interrupt,     /* .INTERRUPT */
                    177:     Libs,          /* .LIBS */
1.165     sjg       178:     Meta,          /* .META */
1.1       cgd       179:     MFlags,        /* .MFLAGS or .MAKEFLAGS */
                    180:     Main,          /* .MAIN and we don't have anything user-specified to
                    181:                     * make */
1.5       cgd       182:     NoExport,      /* .NOEXPORT */
1.165     sjg       183:     NoMeta,        /* .NOMETA */
                    184:     NoMetaCmp,     /* .NOMETA_CMP */
1.32      gwr       185:     NoPath,        /* .NOPATH */
1.1       cgd       186:     Not,           /* Not special */
1.75      tv        187:     NotParallel,    /* .NOTPARALLEL */
1.1       cgd       188:     Null,          /* .NULL */
1.75      tv        189:     ExObjdir,      /* .OBJDIR */
1.1       cgd       190:     Order,         /* .ORDER */
1.18      christos  191:     Parallel,      /* .PARALLEL */
1.5       cgd       192:     ExPath,        /* .PATH */
1.22      christos  193:     Phony,         /* .PHONY */
1.48      sjg       194: #ifdef POSIX
                    195:     Posix,         /* .POSIX */
                    196: #endif
1.1       cgd       197:     Precious,      /* .PRECIOUS */
1.5       cgd       198:     ExShell,       /* .SHELL */
1.1       cgd       199:     Silent,        /* .SILENT */
                    200:     SingleShell,    /* .SINGLESHELL */
1.187     christos  201:     Stale,         /* .STALE */
1.1       cgd       202:     Suffixes,      /* .SUFFIXES */
1.18      christos  203:     Wait,          /* .WAIT */
1.5       cgd       204:     Attribute      /* Generic attribute */
1.1       cgd       205: } ParseSpecial;
                    206:
1.166     dholland  207: /*
                    208:  * Other tokens
                    209:  */
                    210: #define LPAREN '('
                    211: #define RPAREN ')'
                    212:
                    213:
1.248     rillig    214: /* result data */
1.166     dholland  215:
                    216: /*
                    217:  * The main target to create. This is the first target on the first
                    218:  * dependency line in the first makefile.
                    219:  */
                    220: static GNode *mainNode;
                    221:
1.248     rillig    222: /* eval state */
1.166     dholland  223:
                    224: /* targets we're working on */
                    225: static Lst targets;
                    226:
                    227: #ifdef CLEANUP
                    228: /* command lines for targets */
                    229: static Lst targCmds;
                    230: #endif
                    231:
                    232: /*
                    233:  * specType contains the SPECial TYPE of the current target. It is
                    234:  * Not if the target is unspecial. If it *is* special, however, the children
                    235:  * are linked as children of the parent but not vice versa. This variable is
                    236:  * set in ParseDoDependency
                    237:  */
1.5       cgd       238: static ParseSpecial specType;
1.1       cgd       239:
                    240: /*
1.152     dsl       241:  * Predecessor node for handling .ORDER. Initialized to NULL when .ORDER
1.1       cgd       242:  * seen, then set to each successive source on the line.
                    243:  */
                    244: static GNode   *predecessor;
                    245:
1.248     rillig    246: /* parser state */
1.166     dholland  247:
                    248: /* true if currently in a dependency line or its commands */
                    249: static Boolean inLine;
                    250:
                    251: /* number of fatal errors */
                    252: static int fatals = 0;
                    253:
                    254: /*
                    255:  * Variables for doing includes
                    256:  */
                    257:
                    258: /* current file being read */
                    259: static IFile *curFile;
                    260:
1.276     rillig    261: /* The current file from the command line (at the bottom of the stack) and
                    262:  * further up all the files that are currently being read due to nested
1.281     rillig    263:  * .include or .for directives. */
1.276     rillig    264: static Stack /* of *IFile */ includes;
1.166     dholland  265:
                    266: /* include paths (lists of directories) */
                    267: Lst parseIncPath;      /* dirs for "..." includes */
                    268: Lst sysIncPath;                /* dirs for <...> includes */
                    269: Lst defIncPath;                /* default for sysIncPath */
                    270:
1.248     rillig    271: /* parser tables */
1.166     dholland  272:
1.1       cgd       273: /*
                    274:  * The parseKeywords table is searched using binary search when deciding
                    275:  * if a target or source is special. The 'spec' field is the ParseSpecial
                    276:  * type of the keyword ("Not" if the keyword isn't special as a target) while
                    277:  * the 'op' field is the operator to apply to the list of targets if the
                    278:  * keyword is used as a source ("0" if the keyword isn't special as a source)
                    279:  */
1.168     dholland  280: static const struct {
1.93      christos  281:     const char   *name;        /* Name of keyword */
1.1       cgd       282:     ParseSpecial  spec;                /* Type when used as a target */
                    283:     int                  op;           /* Operator when used as a source */
                    284: } parseKeywords[] = {
                    285: { ".BEGIN",      Begin,        0 },
                    286: { ".DEFAULT",    Default,      0 },
1.215     dholland  287: { ".DELETE_ON_ERROR", DeleteOnError, 0 },
1.1       cgd       288: { ".END",        End,          0 },
1.162     sjg       289: { ".ERROR",      dotError,     0 },
1.1       cgd       290: { ".EXEC",       Attribute,    OP_EXEC },
                    291: { ".IGNORE",     Ignore,       OP_IGNORE },
                    292: { ".INCLUDES",   Includes,     0 },
                    293: { ".INTERRUPT",          Interrupt,    0 },
                    294: { ".INVISIBLE",          Attribute,    OP_INVISIBLE },
                    295: { ".JOIN",       Attribute,    OP_JOIN },
                    296: { ".LIBS",       Libs,         0 },
1.29      christos  297: { ".MADE",       Attribute,    OP_MADE },
1.1       cgd       298: { ".MAIN",       Main,         0 },
                    299: { ".MAKE",       Attribute,    OP_MAKE },
                    300: { ".MAKEFLAGS",          MFlags,       0 },
1.165     sjg       301: { ".META",       Meta,         OP_META },
1.1       cgd       302: { ".MFLAGS",     MFlags,       0 },
1.165     sjg       303: { ".NOMETA",     NoMeta,       OP_NOMETA },
                    304: { ".NOMETA_CMP",  NoMetaCmp,   OP_NOMETA_CMP },
1.32      gwr       305: { ".NOPATH",     NoPath,       OP_NOPATH },
1.1       cgd       306: { ".NOTMAIN",    Attribute,    OP_NOTMAIN },
                    307: { ".NOTPARALLEL", NotParallel, 0 },
1.18      christos  308: { ".NO_PARALLEL", NotParallel, 0 },
1.1       cgd       309: { ".NULL",       Null,         0 },
1.75      tv        310: { ".OBJDIR",     ExObjdir,     0 },
1.14      ws        311: { ".OPTIONAL",   Attribute,    OP_OPTIONAL },
1.1       cgd       312: { ".ORDER",      Order,        0 },
1.18      christos  313: { ".PARALLEL",   Parallel,     0 },
1.5       cgd       314: { ".PATH",       ExPath,       0 },
1.22      christos  315: { ".PHONY",      Phony,        OP_PHONY },
1.48      sjg       316: #ifdef POSIX
                    317: { ".POSIX",      Posix,        0 },
                    318: #endif
1.1       cgd       319: { ".PRECIOUS",   Precious,     OP_PRECIOUS },
                    320: { ".RECURSIVE",          Attribute,    OP_MAKE },
1.5       cgd       321: { ".SHELL",      ExShell,      0 },
1.1       cgd       322: { ".SILENT",     Silent,       OP_SILENT },
                    323: { ".SINGLESHELL", SingleShell, 0 },
1.187     christos  324: { ".STALE",      Stale,        0 },
1.1       cgd       325: { ".SUFFIXES",   Suffixes,     0 },
                    326: { ".USE",        Attribute,    OP_USE },
1.71      christos  327: { ".USEBEFORE",   Attribute,           OP_USEBEFORE },
1.18      christos  328: { ".WAIT",       Wait,         0 },
1.1       cgd       329: };
                    330:
1.248     rillig    331: /* file loader */
1.170     dholland  332:
                    333: struct loadedfile {
                    334:        const char *path;               /* name, for error reports */
                    335:        char *buf;                      /* contents buffer */
                    336:        size_t len;                     /* length of contents */
                    337:        size_t maplen;                  /* length of mmap area, or 0 */
                    338:        Boolean used;                   /* XXX: have we used the data yet */
                    339: };
                    340:
                    341: static struct loadedfile *
                    342: loadedfile_create(const char *path)
                    343: {
                    344:        struct loadedfile *lf;
                    345:
                    346:        lf = bmake_malloc(sizeof(*lf));
1.242     rillig    347:        lf->path = path == NULL ? "(stdin)" : path;
1.170     dholland  348:        lf->buf = NULL;
                    349:        lf->len = 0;
                    350:        lf->maplen = 0;
                    351:        lf->used = FALSE;
                    352:        return lf;
                    353: }
                    354:
                    355: static void
                    356: loadedfile_destroy(struct loadedfile *lf)
                    357: {
                    358:        if (lf->buf != NULL) {
                    359:                if (lf->maplen > 0) {
                    360:                        munmap(lf->buf, lf->maplen);
                    361:                } else {
                    362:                        free(lf->buf);
                    363:                }
                    364:        }
                    365:        free(lf);
                    366: }
                    367:
                    368: /*
                    369:  * nextbuf() operation for loadedfile, as needed by the weird and twisted
                    370:  * logic below. Once that's cleaned up, we can get rid of lf->used...
                    371:  */
                    372: static char *
                    373: loadedfile_nextbuf(void *x, size_t *len)
                    374: {
                    375:        struct loadedfile *lf = x;
                    376:
                    377:        if (lf->used) {
                    378:                return NULL;
                    379:        }
                    380:        lf->used = TRUE;
                    381:        *len = lf->len;
                    382:        return lf->buf;
                    383: }
                    384:
                    385: /*
                    386:  * Try to get the size of a file.
                    387:  */
1.272     rillig    388: static Boolean
1.170     dholland  389: load_getsize(int fd, size_t *ret)
                    390: {
                    391:        struct stat st;
                    392:
                    393:        if (fstat(fd, &st) < 0) {
1.272     rillig    394:                return FALSE;
1.170     dholland  395:        }
                    396:
                    397:        if (!S_ISREG(st.st_mode)) {
1.272     rillig    398:                return FALSE;
1.170     dholland  399:        }
                    400:
                    401:        /*
                    402:         * st_size is an off_t, which is 64 bits signed; *ret is
                    403:         * size_t, which might be 32 bits unsigned or 64 bits
                    404:         * unsigned. Rather than being elaborate, just punt on
                    405:         * files that are more than 2^31 bytes. We should never
                    406:         * see a makefile that size in practice...
                    407:         *
                    408:         * While we're at it reject negative sizes too, just in case.
                    409:         */
                    410:        if (st.st_size < 0 || st.st_size > 0x7fffffff) {
1.272     rillig    411:                return FALSE;
1.170     dholland  412:        }
                    413:
                    414:        *ret = (size_t) st.st_size;
1.272     rillig    415:        return TRUE;
1.170     dholland  416: }
                    417:
                    418: /*
                    419:  * Read in a file.
                    420:  *
                    421:  * Until the path search logic can be moved under here instead of
                    422:  * being in the caller in another source file, we need to have the fd
                    423:  * passed in already open. Bleh.
                    424:  *
                    425:  * If the path is NULL use stdin and (to insure against fd leaks)
                    426:  * assert that the caller passed in -1.
                    427:  */
                    428: static struct loadedfile *
                    429: loadfile(const char *path, int fd)
                    430: {
                    431:        struct loadedfile *lf;
1.227     sjg       432:        static long pagesize = 0;
1.170     dholland  433:        ssize_t result;
                    434:        size_t bufpos;
                    435:
                    436:        lf = loadedfile_create(path);
                    437:
                    438:        if (path == NULL) {
                    439:                assert(fd == -1);
                    440:                fd = STDIN_FILENO;
                    441:        } else {
                    442: #if 0 /* notyet */
                    443:                fd = open(path, O_RDONLY);
                    444:                if (fd < 0) {
                    445:                        ...
                    446:                        Error("%s: %s", path, strerror(errno));
                    447:                        exit(1);
                    448:                }
                    449: #endif
                    450:        }
                    451:
1.272     rillig    452:        if (load_getsize(fd, &lf->len)) {
1.170     dholland  453:                /* found a size, try mmap */
1.227     sjg       454:                if (pagesize == 0)
                    455:                        pagesize = sysconf(_SC_PAGESIZE);
1.170     dholland  456:                if (pagesize <= 0) {
                    457:                        pagesize = 0x1000;
                    458:                }
                    459:                /* round size up to a page */
                    460:                lf->maplen = pagesize * ((lf->len + pagesize - 1)/pagesize);
                    461:
                    462:                /*
                    463:                 * XXX hack for dealing with empty files; remove when
                    464:                 * we're no longer limited by interfacing to the old
                    465:                 * logic elsewhere in this file.
                    466:                 */
                    467:                if (lf->maplen == 0) {
                    468:                        lf->maplen = pagesize;
                    469:                }
                    470:
                    471:                /*
                    472:                 * FUTURE: remove PROT_WRITE when the parser no longer
                    473:                 * needs to scribble on the input.
                    474:                 */
                    475:                lf->buf = mmap(NULL, lf->maplen, PROT_READ|PROT_WRITE,
                    476:                               MAP_FILE|MAP_COPY, fd, 0);
                    477:                if (lf->buf != MAP_FAILED) {
                    478:                        /* succeeded */
1.178     dsl       479:                        if (lf->len == lf->maplen && lf->buf[lf->len - 1] != '\n') {
1.220     maya      480:                                char *b = bmake_malloc(lf->len + 1);
1.178     dsl       481:                                b[lf->len] = '\n';
                    482:                                memcpy(b, lf->buf, lf->len++);
                    483:                                munmap(lf->buf, lf->maplen);
                    484:                                lf->maplen = 0;
                    485:                                lf->buf = b;
                    486:                        }
1.170     dholland  487:                        goto done;
                    488:                }
                    489:        }
                    490:
                    491:        /* cannot mmap; load the traditional way */
                    492:
                    493:        lf->maplen = 0;
                    494:        lf->len = 1024;
                    495:        lf->buf = bmake_malloc(lf->len);
                    496:
                    497:        bufpos = 0;
                    498:        while (1) {
                    499:                assert(bufpos <= lf->len);
                    500:                if (bufpos == lf->len) {
1.221     riastrad  501:                        if (lf->len > SIZE_MAX/2) {
                    502:                                errno = EFBIG;
                    503:                                Error("%s: file too large", path);
                    504:                                exit(1);
                    505:                        }
1.170     dholland  506:                        lf->len *= 2;
                    507:                        lf->buf = bmake_realloc(lf->buf, lf->len);
                    508:                }
1.221     riastrad  509:                assert(bufpos < lf->len);
1.170     dholland  510:                result = read(fd, lf->buf + bufpos, lf->len - bufpos);
                    511:                if (result < 0) {
                    512:                        Error("%s: read error: %s", path, strerror(errno));
                    513:                        exit(1);
                    514:                }
                    515:                if (result == 0) {
                    516:                        break;
                    517:                }
                    518:                bufpos += result;
                    519:        }
                    520:        assert(bufpos <= lf->len);
1.173     dholland  521:        lf->len = bufpos;
1.170     dholland  522:
                    523:        /* truncate malloc region to actual length (maybe not useful) */
1.172     dholland  524:        if (lf->len > 0) {
1.218     sjg       525:                /* as for mmap case, ensure trailing \n */
                    526:                if (lf->buf[lf->len - 1] != '\n')
                    527:                        lf->len++;
1.172     dholland  528:                lf->buf = bmake_realloc(lf->buf, lf->len);
1.218     sjg       529:                lf->buf[lf->len - 1] = '\n';
1.172     dholland  530:        }
1.170     dholland  531:
                    532: done:
                    533:        if (path != NULL) {
                    534:                close(fd);
                    535:        }
                    536:        return lf;
                    537: }
                    538:
1.248     rillig    539: /* old code */
1.77      christos  540:
1.279     rillig    541: /* Check if the current character is escaped on the current line. */
                    542: static Boolean
1.84      wiz       543: ParseIsEscaped(const char *line, const char *c)
1.77      christos  544: {
1.280     rillig    545:     Boolean active = FALSE;
1.77      christos  546:     for (;;) {
                    547:        if (line == c)
                    548:            return active;
                    549:        if (*--c != '\\')
                    550:            return active;
                    551:        active = !active;
                    552:     }
                    553: }
                    554:
1.278     rillig    555: /* Add the filename and lineno to the GNode so that we remember where it
                    556:  * was first defined. */
                    557: static void
                    558: ParseMark(GNode *gn)
                    559: {
                    560:     gn->fname = curFile->fname;
                    561:     gn->lineno = curFile->lineno;
                    562: }
                    563:
1.1       cgd       564: /*-
                    565:  *----------------------------------------------------------------------
                    566:  * ParseFindKeyword --
                    567:  *     Look in the table of keywords for one matching the given string.
                    568:  *
1.84      wiz       569:  * Input:
                    570:  *     str             String to find
                    571:  *
1.1       cgd       572:  * Results:
                    573:  *     The index of the keyword, or -1 if it isn't there.
                    574:  *
                    575:  * Side Effects:
                    576:  *     None
                    577:  *----------------------------------------------------------------------
                    578:  */
                    579: static int
1.120     dsl       580: ParseFindKeyword(const char *str)
1.1       cgd       581: {
1.84      wiz       582:     int    start, end, cur;
                    583:     int    diff;
1.27      christos  584:
1.1       cgd       585:     start = 0;
                    586:     end = (sizeof(parseKeywords)/sizeof(parseKeywords[0])) - 1;
                    587:
                    588:     do {
                    589:        cur = start + ((end - start) / 2);
1.103     christos  590:        diff = strcmp(str, parseKeywords[cur].name);
1.1       cgd       591:
                    592:        if (diff == 0) {
1.235     rillig    593:            return cur;
1.1       cgd       594:        } else if (diff < 0) {
                    595:            end = cur - 1;
                    596:        } else {
                    597:            start = cur + 1;
                    598:        }
                    599:     } while (start <= end);
1.235     rillig    600:     return -1;
1.1       cgd       601: }
                    602:
1.291     rillig    603: static void
                    604: PrintLocation(FILE *f, const char *cfname, size_t clineno)
                    605: {
                    606:        char dirbuf[MAXPATHLEN+1];
1.299     rillig    607:        const char *dir, *fname;
                    608:        char *dir_freeIt, *fname_freeIt;
1.291     rillig    609:
1.299     rillig    610:        if (*cfname == '/' || strcmp(cfname, "(stdin)") == 0) {
                    611:                (void)fprintf(f, "\"%s\" line %zu: ", cfname, clineno);
                    612:                return;
                    613:        }
1.291     rillig    614:
1.299     rillig    615:        /* Find out which makefile is the culprit.
                    616:         * We try ${.PARSEDIR} and apply realpath(3) if not absolute. */
1.291     rillig    617:
1.299     rillig    618:        dir = Var_Value(".PARSEDIR", VAR_GLOBAL, &dir_freeIt);
                    619:        if (dir == NULL)
                    620:                dir = ".";
                    621:        if (*dir != '/')
                    622:                dir = realpath(dir, dirbuf);
                    623:
                    624:        fname = Var_Value(".PARSEFILE", VAR_GLOBAL, &fname_freeIt);
                    625:        if (fname == NULL) {
                    626:                const char *slash = strrchr(cfname, '/');
                    627:                fname = slash != NULL ? slash + 1 : cfname;
                    628:        }
                    629:
                    630:        (void)fprintf(f, "\"%s/%s\" line %zu: ", dir, fname, clineno);
                    631:        bmake_free(fname_freeIt);
                    632:        bmake_free(dir_freeIt);
1.291     rillig    633: }
                    634:
1.300     rillig    635: /* Print a parse error message, including location information.
1.1       cgd       636:  *
1.300     rillig    637:  * Increment "fatals" if the level is PARSE_FATAL, and continue parsing
                    638:  * until the end of the current top-level makefile, then exit (see
                    639:  * Parse_File).
1.1       cgd       640:  */
1.38      christos  641: static void
1.127     dsl       642: ParseVErrorInternal(FILE *f, const char *cfname, size_t clineno, int type,
1.122     dsl       643:     const char *fmt, va_list ap)
1.38      christos  644: {
1.56      christos  645:        static Boolean fatal_warning_error_printed = FALSE;
                    646:
1.148     sjg       647:        (void)fprintf(f, "%s: ", progname);
1.63      christos  648:
1.291     rillig    649:        if (cfname != NULL)
                    650:                PrintLocation(f, cfname, clineno);
1.38      christos  651:        if (type == PARSE_WARNING)
1.127     dsl       652:                (void)fprintf(f, "warning: ");
                    653:        (void)vfprintf(f, fmt, ap);
                    654:        (void)fprintf(f, "\n");
                    655:        (void)fflush(f);
1.300     rillig    656:
1.226     sjg       657:        if (type == PARSE_INFO)
                    658:                return;
1.56      christos  659:        if (type == PARSE_FATAL || parseWarnFatal)
1.300     rillig    660:                fatals++;
1.56      christos  661:        if (parseWarnFatal && !fatal_warning_error_printed) {
                    662:                Error("parsing warnings being treated as errors");
                    663:                fatal_warning_error_printed = TRUE;
                    664:        }
1.38      christos  665: }
                    666:
1.203     joerg     667: static void
                    668: ParseErrorInternal(const char *cfname, size_t clineno, int type,
                    669:     const char *fmt, ...)
                    670: {
                    671:        va_list ap;
                    672:
                    673:        va_start(ap, fmt);
                    674:        (void)fflush(stdout);
                    675:        ParseVErrorInternal(stderr, cfname, clineno, type, fmt, ap);
                    676:        va_end(ap);
                    677:
                    678:        if (debug_file != stderr && debug_file != stdout) {
                    679:                va_start(ap, fmt);
                    680:                ParseVErrorInternal(debug_file, cfname, clineno, type, fmt, ap);
                    681:                va_end(ap);
                    682:        }
                    683: }
                    684:
1.289     rillig    685: /* External interface to ParseErrorInternal; uses the default filename and
                    686:  * line number.
1.38      christos  687:  *
1.289     rillig    688:  * Fmt is given without a trailing newline. */
1.1       cgd       689: void
1.93      christos  690: Parse_Error(int type, const char *fmt, ...)
1.1       cgd       691: {
                    692:        va_list ap;
1.156     dsl       693:        const char *fname;
                    694:        size_t lineno;
1.84      wiz       695:
1.152     dsl       696:        if (curFile == NULL) {
1.156     dsl       697:                fname = NULL;
                    698:                lineno = 0;
                    699:        } else {
                    700:                fname = curFile->fname;
                    701:                lineno = curFile->lineno;
1.148     sjg       702:        }
1.156     dsl       703:
                    704:        va_start(ap, fmt);
1.163     sjg       705:        (void)fflush(stdout);
1.156     dsl       706:        ParseVErrorInternal(stderr, fname, lineno, type, fmt, ap);
1.1       cgd       707:        va_end(ap);
1.127     dsl       708:
1.131     dsl       709:        if (debug_file != stderr && debug_file != stdout) {
1.127     dsl       710:                va_start(ap, fmt);
1.156     dsl       711:                ParseVErrorInternal(debug_file, fname, lineno, type, fmt, ap);
1.127     dsl       712:                va_end(ap);
                    713:        }
1.1       cgd       714: }
                    715:
1.161     sjg       716:
1.301     rillig    717: /* Parse a .info .warning or .error directive.
1.161     sjg       718:  *
1.301     rillig    719:  * The input is the line minus the ".".  We substitute variables, print the
                    720:  * message and exit(1) (for .error) or just print a warning if the directive
                    721:  * is malformed.
1.161     sjg       722:  */
1.164     sjg       723: static Boolean
1.161     sjg       724: ParseMessage(char *line)
                    725: {
                    726:     int mtype;
1.164     sjg       727:
1.161     sjg       728:     switch(*line) {
                    729:     case 'i':
1.226     sjg       730:        mtype = PARSE_INFO;
1.161     sjg       731:        break;
                    732:     case 'w':
                    733:        mtype = PARSE_WARNING;
                    734:        break;
                    735:     case 'e':
                    736:        mtype = PARSE_FATAL;
                    737:        break;
                    738:     default:
                    739:        Parse_Error(PARSE_WARNING, "invalid syntax: \".%s\"", line);
1.164     sjg       740:        return FALSE;
1.161     sjg       741:     }
                    742:
1.290     rillig    743:     while (ch_isalpha(*line))
1.161     sjg       744:        line++;
1.290     rillig    745:     if (!ch_isspace(*line))
1.164     sjg       746:        return FALSE;                   /* not for us */
1.290     rillig    747:     while (ch_isspace(*line))
1.161     sjg       748:        line++;
                    749:
1.239     rillig    750:     line = Var_Subst(line, VAR_CMD, VARE_WANTRES);
1.161     sjg       751:     Parse_Error(mtype, "%s", line);
                    752:     free(line);
                    753:
                    754:     if (mtype == PARSE_FATAL) {
                    755:        /* Terminate immediately. */
                    756:        exit(1);
                    757:     }
1.164     sjg       758:     return TRUE;
1.161     sjg       759: }
                    760:
1.1       cgd       761: /*-
                    762:  *---------------------------------------------------------------------
                    763:  * ParseLinkSrc  --
                    764:  *     Link the parent node to its new child. Used in a Lst_ForEach by
                    765:  *     ParseDoDependency. If the specType isn't 'Not', the parent
                    766:  *     isn't linked as a parent of the child.
                    767:  *
1.84      wiz       768:  * Input:
                    769:  *     pgnp            The parent node
                    770:  *     cgpn            The child node
                    771:  *
1.1       cgd       772:  * Results:
                    773:  *     Always = 0
                    774:  *
                    775:  * Side Effects:
                    776:  *     New elements are added to the parents list of cgn and the
                    777:  *     children list of cgn. the unmade field of pgn is updated
                    778:  *     to reflect the additional child.
                    779:  *---------------------------------------------------------------------
                    780:  */
                    781: static int
1.157     dsl       782: ParseLinkSrc(void *pgnp, void *cgnp)
1.1       cgd       783: {
1.105     christos  784:     GNode          *pgn = (GNode *)pgnp;
                    785:     GNode          *cgn = (GNode *)cgnp;
1.52      mycroft   786:
1.268     rillig    787:     if ((pgn->type & OP_DOUBLEDEP) && !Lst_IsEmpty(pgn->cohorts))
1.274     rillig    788:        pgn = LstNode_Datum(Lst_Last(pgn->cohorts));
1.268     rillig    789:     Lst_Append(pgn->children, cgn);
1.52      mycroft   790:     if (specType == Not)
1.268     rillig    791:        Lst_Append(cgn->parents, pgn);
1.52      mycroft   792:     pgn->unmade += 1;
1.109     dsl       793:     if (DEBUG(PARSE)) {
1.193     christos  794:        fprintf(debug_file, "# %s: added child %s - %s\n", __func__,
                    795:            pgn->name, cgn->name);
1.109     dsl       796:        Targ_PrintNode(pgn, 0);
                    797:        Targ_PrintNode(cgn, 0);
                    798:     }
1.235     rillig    799:     return 0;
1.1       cgd       800: }
                    801:
                    802: /*-
                    803:  *---------------------------------------------------------------------
                    804:  * ParseDoOp  --
                    805:  *     Apply the parsed operator to the given target node. Used in a
                    806:  *     Lst_ForEach call by ParseDoDependency once all targets have
                    807:  *     been found and their operator parsed. If the previous and new
                    808:  *     operators are incompatible, a major error is taken.
                    809:  *
1.84      wiz       810:  * Input:
                    811:  *     gnp             The node to which the operator is to be applied
                    812:  *     opp             The operator to apply
                    813:  *
1.1       cgd       814:  * Results:
                    815:  *     Always 0
                    816:  *
                    817:  * Side Effects:
                    818:  *     The type field of the node is altered to reflect any new bits in
                    819:  *     the op.
                    820:  *---------------------------------------------------------------------
                    821:  */
                    822: static int
1.157     dsl       823: ParseDoOp(void *gnp, void *opp)
1.1       cgd       824: {
1.105     christos  825:     GNode          *gn = (GNode *)gnp;
                    826:     int             op = *(int *)opp;
1.1       cgd       827:     /*
                    828:      * If the dependency mask of the operator and the node don't match and
                    829:      * the node has actually had an operator applied to it before, and
1.27      christos  830:      * the operator actually has some dependency information in it, complain.
1.1       cgd       831:      */
                    832:     if (((op & OP_OPMASK) != (gn->type & OP_OPMASK)) &&
                    833:        !OP_NOP(gn->type) && !OP_NOP(op))
                    834:     {
1.97      christos  835:        Parse_Error(PARSE_FATAL, "Inconsistent operator for %s", gn->name);
1.235     rillig    836:        return 1;
1.1       cgd       837:     }
                    838:
1.242     rillig    839:     if (op == OP_DOUBLEDEP && (gn->type & OP_OPMASK) == OP_DOUBLEDEP) {
1.1       cgd       840:        /*
                    841:         * If the node was the object of a :: operator, we need to create a
                    842:         * new instance of it for the children and commands on this dependency
                    843:         * line. The new instance is placed on the 'cohorts' list of the
                    844:         * initial one (note the initial one is not on its own cohorts list)
                    845:         * and the new instance is linked to all parents of the initial
                    846:         * instance.
                    847:         */
1.84      wiz       848:        GNode   *cohort;
1.27      christos  849:
1.33      mycroft   850:        /*
1.46      mycroft   851:         * Propagate copied bits to the initial node.  They'll be propagated
                    852:         * back to the rest of the cohorts later.
1.33      mycroft   853:         */
1.46      mycroft   854:        gn->type |= op & ~OP_OPMASK;
1.33      mycroft   855:
1.120     dsl       856:        cohort = Targ_FindNode(gn->name, TARG_NOHASH);
1.186     christos  857:        if (doing_depend)
                    858:            ParseMark(cohort);
1.1       cgd       859:        /*
                    860:         * Make the cohort invisible as well to avoid duplicating it into
                    861:         * other variables. True, parents of this target won't tend to do
                    862:         * anything with their local variables, but better safe than
1.46      mycroft   863:         * sorry. (I think this is pointless now, since the relevant list
                    864:         * traversals will no longer see this node anyway. -mycroft)
1.1       cgd       865:         */
1.46      mycroft   866:        cohort->type = op | OP_INVISIBLE;
1.268     rillig    867:        Lst_Append(gn->cohorts, cohort);
1.83      pk        868:        cohort->centurion = gn;
                    869:        gn->unmade_cohorts += 1;
1.120     dsl       870:        snprintf(cohort->cohort_num, sizeof cohort->cohort_num, "#%d",
                    871:                gn->unmade_cohorts);
1.46      mycroft   872:     } else {
1.1       cgd       873:        /*
1.46      mycroft   874:         * We don't want to nuke any previous flags (whatever they were) so we
                    875:         * just OR the new operator into the old
1.1       cgd       876:         */
1.46      mycroft   877:        gn->type |= op;
1.1       cgd       878:     }
1.33      mycroft   879:
1.235     rillig    880:     return 0;
1.1       cgd       881: }
                    882:
1.27      christos  883: /*-
1.18      christos  884:  *---------------------------------------------------------------------
1.1       cgd       885:  * ParseDoSrc  --
                    886:  *     Given the name of a source, figure out if it is an attribute
                    887:  *     and apply it to the targets if it is. Else decide if there is
                    888:  *     some attribute which should be applied *to* the source because
                    889:  *     of some special target and apply it if so. Otherwise, make the
                    890:  *     source be a child of the targets in the list 'targets'
                    891:  *
1.84      wiz       892:  * Input:
                    893:  *     tOp             operator (if any) from special targets
                    894:  *     src             name of the source to handle
                    895:  *
1.1       cgd       896:  * Results:
                    897:  *     None
                    898:  *
                    899:  * Side Effects:
                    900:  *     Operator bits may be added to the list of targets or to the source.
                    901:  *     The targets may have a new source added to their lists of children.
                    902:  *---------------------------------------------------------------------
                    903:  */
                    904: static void
1.120     dsl       905: ParseDoSrc(int tOp, const char *src)
1.1       cgd       906: {
1.18      christos  907:     GNode      *gn = NULL;
1.120     dsl       908:     static int wait_number = 0;
                    909:     char wait_src[16];
1.1       cgd       910:
1.290     rillig    911:     if (*src == '.' && ch_isupper(src[1])) {
1.1       cgd       912:        int keywd = ParseFindKeyword(src);
                    913:        if (keywd != -1) {
1.18      christos  914:            int op = parseKeywords[keywd].op;
                    915:            if (op != 0) {
1.265     rillig    916:                if (targets != NULL)
1.268     rillig    917:                    Lst_ForEach(targets, ParseDoOp, &op);
1.18      christos  918:                return;
                    919:            }
                    920:            if (parseKeywords[keywd].spec == Wait) {
1.120     dsl       921:                /*
                    922:                 * We add a .WAIT node in the dependency list.
                    923:                 * After any dynamic dependencies (and filename globbing)
                    924:                 * have happened, it is given a dependency on the each
                    925:                 * previous child back to and previous .WAIT node.
                    926:                 * The next child won't be scheduled until the .WAIT node
                    927:                 * is built.
                    928:                 * We give each .WAIT node a unique name (mainly for diag).
                    929:                 */
                    930:                snprintf(wait_src, sizeof wait_src, ".WAIT_%u", ++wait_number);
                    931:                gn = Targ_FindNode(wait_src, TARG_NOHASH);
1.186     christos  932:                if (doing_depend)
                    933:                    ParseMark(gn);
1.120     dsl       934:                gn->type = OP_WAIT | OP_PHONY | OP_DEPENDS | OP_NOTMAIN;
1.265     rillig    935:                if (targets != NULL)
1.268     rillig    936:                    Lst_ForEach(targets, ParseLinkSrc, gn);
1.18      christos  937:                return;
                    938:            }
1.1       cgd       939:        }
                    940:     }
1.18      christos  941:
                    942:     switch (specType) {
                    943:     case Main:
1.1       cgd       944:        /*
                    945:         * If we have noted the existence of a .MAIN, it means we need
                    946:         * to add the sources of said target to the list of things
                    947:         * to create. The string 'src' is likely to be free, so we
                    948:         * must make a new copy of it. Note that this will only be
                    949:         * invoked if the user didn't specify a target on the command
                    950:         * line. This is to allow #ifmake's to succeed, or something...
                    951:         */
1.268     rillig    952:        Lst_Append(create, bmake_strdup(src));
1.1       cgd       953:        /*
1.118     dsl       954:         * Add the name to the .TARGETS variable as well, so the user can
1.1       cgd       955:         * employ that, if desired.
                    956:         */
                    957:        Var_Append(".TARGETS", src, VAR_GLOBAL);
1.18      christos  958:        return;
                    959:
                    960:     case Order:
1.1       cgd       961:        /*
                    962:         * Create proper predecessor/successor links between the previous
                    963:         * source and the current one.
                    964:         */
                    965:        gn = Targ_FindNode(src, TARG_CREATE);
1.186     christos  966:        if (doing_depend)
                    967:            ParseMark(gn);
1.152     dsl       968:        if (predecessor != NULL) {
1.268     rillig    969:            Lst_Append(predecessor->order_succ, gn);
                    970:            Lst_Append(gn->order_pred, predecessor);
1.109     dsl       971:            if (DEBUG(PARSE)) {
1.193     christos  972:                fprintf(debug_file, "# %s: added Order dependency %s - %s\n",
                    973:                    __func__, predecessor->name, gn->name);
1.109     dsl       974:                Targ_PrintNode(predecessor, 0);
                    975:                Targ_PrintNode(gn, 0);
                    976:            }
1.1       cgd       977:        }
                    978:        /*
                    979:         * The current source now becomes the predecessor for the next one.
                    980:         */
                    981:        predecessor = gn;
1.18      christos  982:        break;
                    983:
                    984:     default:
1.1       cgd       985:        /*
                    986:         * If the source is not an attribute, we need to find/create
                    987:         * a node for it. After that we can apply any operator to it
                    988:         * from a special target or link it to its parents, as
                    989:         * appropriate.
                    990:         *
                    991:         * In the case of a source that was the object of a :: operator,
                    992:         * the attribute is applied to all of its instances (as kept in
                    993:         * the 'cohorts' list of the node) or all the cohorts are linked
                    994:         * to all the targets.
                    995:         */
1.118     dsl       996:
                    997:        /* Find/create the 'src' node and attach to all targets */
1.97      christos  998:        gn = Targ_FindNode(src, TARG_CREATE);
1.186     christos  999:        if (doing_depend)
                   1000:            ParseMark(gn);
1.1       cgd      1001:        if (tOp) {
                   1002:            gn->type |= tOp;
                   1003:        } else {
1.265     rillig   1004:            if (targets != NULL)
1.268     rillig   1005:                Lst_ForEach(targets, ParseLinkSrc, gn);
1.1       cgd      1006:        }
1.18      christos 1007:        break;
                   1008:     }
1.1       cgd      1009: }
                   1010:
                   1011: /*-
                   1012:  *-----------------------------------------------------------------------
                   1013:  * ParseFindMain --
                   1014:  *     Find a real target in the list and set it to be the main one.
                   1015:  *     Called by ParseDoDependency when a main target hasn't been found
                   1016:  *     yet.
                   1017:  *
1.84      wiz      1018:  * Input:
                   1019:  *     gnp             Node to examine
                   1020:  *
1.1       cgd      1021:  * Results:
                   1022:  *     0 if main not found yet, 1 if it is.
                   1023:  *
                   1024:  * Side Effects:
                   1025:  *     mainNode is changed and Targ_SetMain is called.
                   1026:  *
                   1027:  *-----------------------------------------------------------------------
                   1028:  */
                   1029: static int
1.219     riastrad 1030: ParseFindMain(void *gnp, void *dummy MAKE_ATTR_UNUSED)
1.1       cgd      1031: {
1.105     christos 1032:     GNode        *gn = (GNode *)gnp;
1.242     rillig   1033:     if (!(gn->type & OP_NOTARGET)) {
1.1       cgd      1034:        mainNode = gn;
                   1035:        Targ_SetMain(gn);
1.219     riastrad 1036:        return 1;
1.1       cgd      1037:     } else {
1.219     riastrad 1038:        return 0;
1.1       cgd      1039:     }
                   1040: }
                   1041:
                   1042: /*-
                   1043:  *-----------------------------------------------------------------------
                   1044:  * ParseAddDir --
                   1045:  *     Front-end for Dir_AddDir to make sure Lst_ForEach keeps going
                   1046:  *
                   1047:  * Results:
                   1048:  *     === 0
                   1049:  *
                   1050:  * Side Effects:
                   1051:  *     See Dir_AddDir.
                   1052:  *
                   1053:  *-----------------------------------------------------------------------
                   1054:  */
                   1055: static int
1.157     dsl      1056: ParseAddDir(void *path, void *name)
1.1       cgd      1057: {
1.105     christos 1058:     (void)Dir_AddDir((Lst) path, (char *)name);
1.235     rillig   1059:     return 0;
1.1       cgd      1060: }
                   1061:
                   1062: /*-
                   1063:  *-----------------------------------------------------------------------
                   1064:  * ParseClearPath --
                   1065:  *     Front-end for Dir_ClearPath to make sure Lst_ForEach keeps going
                   1066:  *
                   1067:  * Results:
                   1068:  *     === 0
                   1069:  *
                   1070:  * Side Effects:
                   1071:  *     See Dir_ClearPath
                   1072:  *
                   1073:  *-----------------------------------------------------------------------
                   1074:  */
                   1075: static int
1.219     riastrad 1076: ParseClearPath(void *path, void *dummy MAKE_ATTR_UNUSED)
1.1       cgd      1077: {
1.9       jtc      1078:     Dir_ClearPath((Lst) path);
1.219     riastrad 1079:     return 0;
1.1       cgd      1080: }
                   1081:
                   1082: /*-
                   1083:  *---------------------------------------------------------------------
                   1084:  * ParseDoDependency  --
                   1085:  *     Parse the dependency line in line.
                   1086:  *
1.84      wiz      1087:  * Input:
                   1088:  *     line            the line to parse
                   1089:  *
1.1       cgd      1090:  * Results:
                   1091:  *     None
                   1092:  *
                   1093:  * Side Effects:
                   1094:  *     The nodes of the sources are linked as children to the nodes of the
                   1095:  *     targets. Some nodes may be created.
                   1096:  *
                   1097:  *     We parse a dependency line by first extracting words from the line and
                   1098:  * finding nodes in the list of all targets with that name. This is done
                   1099:  * until a character is encountered which is an operator character. Currently
                   1100:  * these are only ! and :. At this point the operator is parsed and the
                   1101:  * pointer into the line advanced until the first source is encountered.
                   1102:  *     The parsed operator is applied to each node in the 'targets' list,
                   1103:  * which is where the nodes found for the targets are kept, by means of
                   1104:  * the ParseDoOp function.
                   1105:  *     The sources are read in much the same way as the targets were except
                   1106:  * that now they are expanded using the wildcarding scheme of the C-Shell
                   1107:  * and all instances of the resulting words in the list of all targets
                   1108:  * are found. Each of the resulting nodes is then linked to each of the
                   1109:  * targets as one of its children.
                   1110:  *     Certain targets are handled specially. These are the ones detailed
                   1111:  * by the specType variable.
                   1112:  *     The storing of transformation rules is also taken care of here.
                   1113:  * A target is recognized as a transformation rule by calling
                   1114:  * Suff_IsTransform. If it is a transformation rule, its node is gotten
                   1115:  * from the suffix module via Suff_AddTransform rather than the standard
                   1116:  * Targ_FindNode in the target module.
                   1117:  *---------------------------------------------------------------------
                   1118:  */
                   1119: static void
1.84      wiz      1120: ParseDoDependency(char *line)
1.1       cgd      1121: {
1.9       jtc      1122:     char          *cp;         /* our current position */
1.98      christos 1123:     GNode         *gn = NULL;  /* a general purpose temporary node */
1.9       jtc      1124:     int             op;                /* the operator on the line */
1.1       cgd      1125:     char            savec;     /* a place to save a character */
                   1126:     Lst            paths;      /* List of search paths to alter when parsing
                   1127:                                 * a list of .PATH targets */
                   1128:     int                    tOp;        /* operator from special target */
1.18      christos 1129:     Lst                    sources;    /* list of archive source names after
                   1130:                                 * expansion */
1.1       cgd      1131:     Lst            curTargs;   /* list of target names to be found and added
                   1132:                                 * to the targets list */
1.77      christos 1133:     char          *lstart = line;
1.1       cgd      1134:
1.120     dsl      1135:     if (DEBUG(PARSE))
                   1136:        fprintf(debug_file, "ParseDoDependency(%s)\n", line);
1.1       cgd      1137:     tOp = 0;
                   1138:
                   1139:     specType = Not;
1.179     plunky   1140:     paths = NULL;
1.1       cgd      1141:
1.252     rillig   1142:     curTargs = Lst_Init();
1.27      christos 1143:
1.204     dholland 1144:     /*
                   1145:      * First, grind through the targets.
                   1146:      */
                   1147:
1.1       cgd      1148:     do {
1.204     dholland 1149:        /*
                   1150:         * Here LINE points to the beginning of the next word, and
                   1151:         * LSTART points to the actual beginning of the line.
                   1152:         */
                   1153:
                   1154:        /* Find the end of the next word. */
1.203     joerg    1155:        for (cp = line; *cp && (ParseIsEscaped(lstart, cp) ||
1.290     rillig   1156:                     !(ch_isspace(*cp) ||
1.287     rillig   1157:                         *cp == '!' || *cp == ':' || *cp == LPAREN));) {
1.1       cgd      1158:            if (*cp == '$') {
                   1159:                /*
                   1160:                 * Must be a dynamic source (would have been expanded
                   1161:                 * otherwise), so call the Var module to parse the puppy
                   1162:                 * so we can safely advance beyond it...There should be
                   1163:                 * no errors in this, as they would have been discovered
                   1164:                 * in the initial Var_Subst and we wouldn't be here.
                   1165:                 */
1.287     rillig   1166:                const char *nested_p = cp;
1.114     christos 1167:                void    *freeIt;
1.1       cgd      1168:
1.294     rillig   1169:                (void)Var_Parse(&nested_p, VAR_CMD,
                   1170:                                VARE_UNDEFERR|VARE_WANTRES, &freeIt);
1.209     christos 1171:                free(freeIt);
1.287     rillig   1172:                cp += nested_p - cp;
                   1173:            } else
1.292     rillig   1174:                cp++;
1.1       cgd      1175:        }
1.121     dsl      1176:
1.204     dholland 1177:        /*
                   1178:         * If the word is followed by a left parenthesis, it's the
                   1179:         * name of an object file inside an archive (ar file).
                   1180:         */
1.77      christos 1181:        if (!ParseIsEscaped(lstart, cp) && *cp == LPAREN) {
1.1       cgd      1182:            /*
1.203     joerg    1183:             * Archives must be handled specially to make sure the OP_ARCHV
                   1184:             * flag is set in their 'type' field, for one thing, and because
                   1185:             * things like "archive(file1.o file2.o file3.o)" are permissible.
                   1186:             * Arch_ParseArchive will set 'line' to be the first non-blank
                   1187:             * after the archive-spec. It creates/finds nodes for the members
1.272     rillig   1188:             * and places them on the given list, returning TRUE if all
                   1189:             * went well and FALSE if there was an error in the
1.203     joerg    1190:             * specification. On error, line should remain untouched.
1.1       cgd      1191:             */
1.264     rillig   1192:            if (!Arch_ParseArchive(&line, targets, VAR_CMD)) {
1.97      christos 1193:                Parse_Error(PARSE_FATAL,
1.203     joerg    1194:                             "Error in archive specification: \"%s\"", line);
1.112     christos 1195:                goto out;
1.203     joerg    1196:            } else {
1.204     dholland 1197:                /* Done with this word; on to the next. */
1.213     matthias 1198:                cp = line;
1.1       cgd      1199:                continue;
1.203     joerg    1200:            }
1.1       cgd      1201:        }
1.27      christos 1202:
1.1       cgd      1203:        if (!*cp) {
                   1204:            /*
1.204     dholland 1205:             * We got to the end of the line while we were still
                   1206:             * looking at targets.
                   1207:             *
1.1       cgd      1208:             * Ending a dependency line without an operator is a Bozo
1.65      sommerfe 1209:             * no-no.  As a heuristic, this is also often triggered by
                   1210:             * undetected conflicts from cvs/rcs merges.
1.1       cgd      1211:             */
1.65      sommerfe 1212:            if ((strncmp(line, "<<<<<<", 6) == 0) ||
                   1213:                (strncmp(line, "======", 6) == 0) ||
                   1214:                (strncmp(line, ">>>>>>", 6) == 0))
1.97      christos 1215:                Parse_Error(PARSE_FATAL,
1.67      sommerfe 1216:                    "Makefile appears to contain unresolved cvs/rcs/??? merge conflicts");
1.240     rillig   1217:            else if (lstart[0] == '.') {
                   1218:                const char *dirstart = lstart + 1;
1.247     rillig   1219:                const char *dirend;
1.290     rillig   1220:                while (ch_isspace(*dirstart))
1.240     rillig   1221:                    dirstart++;
1.247     rillig   1222:                dirend = dirstart;
1.290     rillig   1223:                while (ch_isalnum(*dirend) || *dirend == '-')
1.240     rillig   1224:                    dirend++;
                   1225:                Parse_Error(PARSE_FATAL, "Unknown directive \"%.*s\"",
                   1226:                            (int)(dirend - dirstart), dirstart);
                   1227:            } else
1.241     rillig   1228:                Parse_Error(PARSE_FATAL, "Need an operator");
1.112     christos 1229:            goto out;
1.1       cgd      1230:        }
1.204     dholland 1231:
                   1232:        /* Insert a null terminator. */
                   1233:        savec = *cp;
1.1       cgd      1234:        *cp = '\0';
1.118     dsl      1235:
1.1       cgd      1236:        /*
1.204     dholland 1237:         * Got the word. See if it's a special target and if so set
1.1       cgd      1238:         * specType to match it.
                   1239:         */
1.290     rillig   1240:        if (*line == '.' && ch_isupper(line[1])) {
1.1       cgd      1241:            /*
                   1242:             * See if the target is a special target that must have it
1.27      christos 1243:             * or its sources handled specially.
1.1       cgd      1244:             */
                   1245:            int keywd = ParseFindKeyword(line);
                   1246:            if (keywd != -1) {
1.5       cgd      1247:                if (specType == ExPath && parseKeywords[keywd].spec != ExPath) {
1.1       cgd      1248:                    Parse_Error(PARSE_FATAL, "Mismatched special targets");
1.112     christos 1249:                    goto out;
1.1       cgd      1250:                }
1.27      christos 1251:
1.1       cgd      1252:                specType = parseKeywords[keywd].spec;
                   1253:                tOp = parseKeywords[keywd].op;
                   1254:
                   1255:                /*
                   1256:                 * Certain special targets have special semantics:
                   1257:                 *      .PATH           Have to set the dirSearchPath
                   1258:                 *                      variable too
                   1259:                 *      .MAIN           Its sources are only used if
                   1260:                 *                      nothing has been specified to
                   1261:                 *                      create.
                   1262:                 *      .DEFAULT        Need to create a node to hang
                   1263:                 *                      commands on, but we don't want
                   1264:                 *                      it in the graph, nor do we want
                   1265:                 *                      it to be the Main Target, so we
                   1266:                 *                      create it, set OP_NOTMAIN and
                   1267:                 *                      add it to the list, setting
                   1268:                 *                      DEFAULT to the new node for
                   1269:                 *                      later use. We claim the node is
                   1270:                 *                      A transformation rule to make
                   1271:                 *                      life easier later, when we'll
                   1272:                 *                      use Make_HandleUse to actually
                   1273:                 *                      apply the .DEFAULT commands.
1.22      christos 1274:                 *      .PHONY          The list of targets
1.32      gwr      1275:                 *      .NOPATH         Don't search for file in the path
1.187     christos 1276:                 *      .STALE
1.1       cgd      1277:                 *      .BEGIN
                   1278:                 *      .END
1.162     sjg      1279:                 *      .ERROR
1.215     dholland 1280:                 *      .DELETE_ON_ERROR
1.1       cgd      1281:                 *      .INTERRUPT      Are not to be considered the
                   1282:                 *                      main target.
                   1283:                 *      .NOTPARALLEL    Make only one target at a time.
                   1284:                 *      .SINGLESHELL    Create a shell for each command.
1.152     dsl      1285:                 *      .ORDER          Must set initial predecessor to NULL
1.1       cgd      1286:                 */
                   1287:                switch (specType) {
1.187     christos 1288:                case ExPath:
                   1289:                    if (paths == NULL) {
1.252     rillig   1290:                        paths = Lst_Init();
1.187     christos 1291:                    }
1.268     rillig   1292:                    Lst_Append(paths, dirSearchPath);
1.187     christos 1293:                    break;
                   1294:                case Main:
1.268     rillig   1295:                    if (!Lst_IsEmpty(create)) {
1.187     christos 1296:                        specType = Not;
                   1297:                    }
                   1298:                    break;
                   1299:                case Begin:
                   1300:                case End:
                   1301:                case Stale:
                   1302:                case dotError:
                   1303:                case Interrupt:
                   1304:                    gn = Targ_FindNode(line, TARG_CREATE);
                   1305:                    if (doing_depend)
                   1306:                        ParseMark(gn);
                   1307:                    gn->type |= OP_NOTMAIN|OP_SPECIAL;
1.268     rillig   1308:                    Lst_Append(targets, gn);
1.187     christos 1309:                    break;
                   1310:                case Default:
                   1311:                    gn = Targ_NewGN(".DEFAULT");
                   1312:                    gn->type |= (OP_NOTMAIN|OP_TRANSFORM);
1.268     rillig   1313:                    Lst_Append(targets, gn);
1.187     christos 1314:                    DEFAULT = gn;
                   1315:                    break;
1.215     dholland 1316:                case DeleteOnError:
                   1317:                    deleteOnError = TRUE;
                   1318:                    break;
1.187     christos 1319:                case NotParallel:
                   1320:                    maxJobs = 1;
                   1321:                    break;
                   1322:                case SingleShell:
                   1323:                    compatMake = TRUE;
                   1324:                    break;
                   1325:                case Order:
                   1326:                    predecessor = NULL;
                   1327:                    break;
                   1328:                default:
                   1329:                    break;
1.1       cgd      1330:                }
1.103     christos 1331:            } else if (strncmp(line, ".PATH", 5) == 0) {
1.1       cgd      1332:                /*
                   1333:                 * .PATH<suffix> has to be handled specially.
                   1334:                 * Call on the suffix module to give us a path to
                   1335:                 * modify.
                   1336:                 */
                   1337:                Lst     path;
1.27      christos 1338:
1.5       cgd      1339:                specType = ExPath;
1.97      christos 1340:                path = Suff_GetPath(&line[5]);
1.152     dsl      1341:                if (path == NULL) {
1.97      christos 1342:                    Parse_Error(PARSE_FATAL,
1.1       cgd      1343:                                 "Suffix '%s' not defined (yet)",
                   1344:                                 &line[5]);
1.112     christos 1345:                    goto out;
1.1       cgd      1346:                } else {
1.179     plunky   1347:                    if (paths == NULL) {
1.252     rillig   1348:                        paths = Lst_Init();
1.1       cgd      1349:                    }
1.268     rillig   1350:                    Lst_Append(paths, path);
1.1       cgd      1351:                }
                   1352:            }
                   1353:        }
1.27      christos 1354:
1.1       cgd      1355:        /*
                   1356:         * Have word in line. Get or create its node and stick it at
1.27      christos 1357:         * the end of the targets list
1.1       cgd      1358:         */
1.242     rillig   1359:        if (specType == Not && *line != '\0') {
1.1       cgd      1360:            if (Dir_HasWildcards(line)) {
                   1361:                /*
                   1362:                 * Targets are to be sought only in the current directory,
                   1363:                 * so create an empty path for the thing. Note we need to
                   1364:                 * use Dir_Destroy in the destruction of the path as the
                   1365:                 * Dir module could have added a directory to the path...
                   1366:                 */
1.252     rillig   1367:                Lst         emptyPath = Lst_Init();
1.27      christos 1368:
1.1       cgd      1369:                Dir_Expand(line, emptyPath, curTargs);
1.27      christos 1370:
1.268     rillig   1371:                Lst_Destroy(emptyPath, Dir_Destroy);
1.1       cgd      1372:            } else {
                   1373:                /*
                   1374:                 * No wildcards, but we want to avoid code duplication,
                   1375:                 * so create a list with the word on it.
                   1376:                 */
1.268     rillig   1377:                Lst_Append(curTargs, line);
1.1       cgd      1378:            }
1.27      christos 1379:
1.204     dholland 1380:            /* Apply the targets. */
                   1381:
1.268     rillig   1382:            while(!Lst_IsEmpty(curTargs)) {
                   1383:                char *targName = Lst_Dequeue(curTargs);
1.27      christos 1384:
1.203     joerg    1385:                if (!Suff_IsTransform (targName)) {
1.97      christos 1386:                    gn = Targ_FindNode(targName, TARG_CREATE);
1.1       cgd      1387:                } else {
1.203     joerg    1388:                    gn = Suff_AddTransform(targName);
1.1       cgd      1389:                }
1.186     christos 1390:                if (doing_depend)
                   1391:                    ParseMark(gn);
1.27      christos 1392:
1.268     rillig   1393:                Lst_Append(targets, gn);
1.1       cgd      1394:            }
1.5       cgd      1395:        } else if (specType == ExPath && *line != '.' && *line != '\0') {
1.1       cgd      1396:            Parse_Error(PARSE_WARNING, "Extra target (%s) ignored", line);
                   1397:        }
1.27      christos 1398:
1.204     dholland 1399:        /* Don't need the inserted null terminator any more. */
1.1       cgd      1400:        *cp = savec;
1.204     dholland 1401:
1.1       cgd      1402:        /*
                   1403:         * If it is a special type and not .PATH, it's the only target we
                   1404:         * allow on this line...
                   1405:         */
1.5       cgd      1406:        if (specType != Not && specType != ExPath) {
1.115     christos 1407:            Boolean warning = FALSE;
1.27      christos 1408:
1.77      christos 1409:            while (*cp && (ParseIsEscaped(lstart, cp) ||
1.242     rillig   1410:                (*cp != '!' && *cp != ':'))) {
1.77      christos 1411:                if (ParseIsEscaped(lstart, cp) ||
                   1412:                    (*cp != ' ' && *cp != '\t')) {
1.115     christos 1413:                    warning = TRUE;
1.1       cgd      1414:                }
                   1415:                cp++;
                   1416:            }
1.115     christos 1417:            if (warning) {
1.1       cgd      1418:                Parse_Error(PARSE_WARNING, "Extra target ignored");
                   1419:            }
                   1420:        } else {
1.290     rillig   1421:            while (*cp && ch_isspace(*cp)) {
1.1       cgd      1422:                cp++;
                   1423:            }
                   1424:        }
1.203     joerg    1425:        line = cp;
                   1426:     } while (*line && (ParseIsEscaped(lstart, line) ||
1.242     rillig   1427:        (*line != '!' && *line != ':')));
1.1       cgd      1428:
                   1429:     /*
                   1430:      * Don't need the list of target names anymore...
                   1431:      */
1.268     rillig   1432:     Lst_Free(curTargs);
1.112     christos 1433:     curTargs = NULL;
1.1       cgd      1434:
1.268     rillig   1435:     if (targets != NULL && !Lst_IsEmpty(targets)) {
1.1       cgd      1436:        switch(specType) {
                   1437:            default:
                   1438:                Parse_Error(PARSE_WARNING, "Special and mundane targets don't mix. Mundane ones ignored");
                   1439:                break;
                   1440:            case Default:
1.187     christos 1441:            case Stale:
1.1       cgd      1442:            case Begin:
                   1443:            case End:
1.162     sjg      1444:            case dotError:
1.1       cgd      1445:            case Interrupt:
                   1446:                /*
                   1447:                 * These four create nodes on which to hang commands, so
                   1448:                 * targets shouldn't be empty...
                   1449:                 */
                   1450:            case Not:
                   1451:                /*
                   1452:                 * Nothing special here -- targets can be empty if it wants.
                   1453:                 */
                   1454:                break;
                   1455:        }
                   1456:     }
                   1457:
                   1458:     /*
                   1459:      * Have now parsed all the target names. Must parse the operator next. The
                   1460:      * result is left in  op .
                   1461:      */
                   1462:     if (*cp == '!') {
                   1463:        op = OP_FORCE;
                   1464:     } else if (*cp == ':') {
                   1465:        if (cp[1] == ':') {
                   1466:            op = OP_DOUBLEDEP;
                   1467:            cp++;
                   1468:        } else {
                   1469:            op = OP_DEPENDS;
                   1470:        }
                   1471:     } else {
1.159     dsl      1472:        Parse_Error(PARSE_FATAL, lstart[0] == '.' ? "Unknown directive"
                   1473:                    : "Missing dependency operator");
1.112     christos 1474:        goto out;
1.1       cgd      1475:     }
                   1476:
1.204     dholland 1477:     /* Advance beyond the operator */
                   1478:     cp++;
1.1       cgd      1479:
1.204     dholland 1480:     /*
                   1481:      * Apply the operator to the target. This is how we remember which
                   1482:      * operator a target was defined with. It fails if the operator
                   1483:      * used isn't consistent across all references.
                   1484:      */
1.265     rillig   1485:     if (targets != NULL)
1.268     rillig   1486:        Lst_ForEach(targets, ParseDoOp, &op);
1.1       cgd      1487:
                   1488:     /*
1.204     dholland 1489:      * Onward to the sources.
                   1490:      *
                   1491:      * LINE will now point to the first source word, if any, or the
                   1492:      * end of the string if not.
1.1       cgd      1493:      */
1.290     rillig   1494:     while (*cp && ch_isspace(*cp)) {
1.1       cgd      1495:        cp++;
                   1496:     }
                   1497:     line = cp;
                   1498:
                   1499:     /*
                   1500:      * Several special targets take different actions if present with no
                   1501:      * sources:
                   1502:      * a .SUFFIXES line with no sources clears out all old suffixes
                   1503:      * a .PRECIOUS line makes all targets precious
                   1504:      * a .IGNORE line ignores errors for all targets
                   1505:      * a .SILENT line creates silence when making all targets
                   1506:      * a .PATH removes all directories from the search path(s).
                   1507:      */
                   1508:     if (!*line) {
                   1509:        switch (specType) {
                   1510:            case Suffixes:
1.97      christos 1511:                Suff_ClearSuffixes();
1.1       cgd      1512:                break;
                   1513:            case Precious:
                   1514:                allPrecious = TRUE;
                   1515:                break;
                   1516:            case Ignore:
                   1517:                ignoreErrors = TRUE;
                   1518:                break;
                   1519:            case Silent:
                   1520:                beSilent = TRUE;
                   1521:                break;
1.5       cgd      1522:            case ExPath:
1.265     rillig   1523:                if (paths != NULL)
1.268     rillig   1524:                    Lst_ForEach(paths, ParseClearPath, NULL);
1.85      sjg      1525:                Dir_SetPATH();
1.1       cgd      1526:                break;
1.48      sjg      1527: #ifdef POSIX
1.246     rillig   1528:            case Posix:
                   1529:                Var_Set("%POSIX", "1003.2", VAR_GLOBAL);
                   1530:                break;
1.48      sjg      1531: #endif
1.5       cgd      1532:            default:
                   1533:                break;
1.1       cgd      1534:        }
                   1535:     } else if (specType == MFlags) {
                   1536:        /*
                   1537:         * Call on functions in main.c to deal with these arguments and
                   1538:         * set the initial character to a null-character so the loop to
                   1539:         * get sources won't get anything
                   1540:         */
1.97      christos 1541:        Main_ParseArgLine(line);
1.1       cgd      1542:        *line = '\0';
1.5       cgd      1543:     } else if (specType == ExShell) {
1.272     rillig   1544:        if (!Job_ParseShell(line)) {
1.97      christos 1545:            Parse_Error(PARSE_FATAL, "improper shell specification");
1.112     christos 1546:            goto out;
1.1       cgd      1547:        }
                   1548:        *line = '\0';
1.242     rillig   1549:     } else if (specType == NotParallel || specType == SingleShell ||
                   1550:            specType == DeleteOnError) {
1.1       cgd      1551:        *line = '\0';
                   1552:     }
1.27      christos 1553:
1.1       cgd      1554:     /*
1.27      christos 1555:      * NOW GO FOR THE SOURCES
1.1       cgd      1556:      */
1.242     rillig   1557:     if (specType == Suffixes || specType == ExPath ||
                   1558:        specType == Includes || specType == Libs ||
                   1559:        specType == Null || specType == ExObjdir)
1.1       cgd      1560:     {
1.203     joerg    1561:        while (*line) {
1.1       cgd      1562:            /*
                   1563:             * If the target was one that doesn't take files as its sources
                   1564:             * but takes something like suffixes, we take each
                   1565:             * space-separated word on the line as a something and deal
                   1566:             * with it accordingly.
                   1567:             *
                   1568:             * If the target was .SUFFIXES, we take each source as a
                   1569:             * suffix and add it to the list of suffixes maintained by the
1.203     joerg    1570:             * Suff module.
1.1       cgd      1571:             *
                   1572:             * If the target was a .PATH, we add the source as a directory
                   1573:             * to search on the search path.
                   1574:             *
                   1575:             * If it was .INCLUDES, the source is taken to be the suffix of
                   1576:             * files which will be #included and whose search path should
                   1577:             * be present in the .INCLUDES variable.
                   1578:             *
                   1579:             * If it was .LIBS, the source is taken to be the suffix of
                   1580:             * files which are considered libraries and whose search path
                   1581:             * should be present in the .LIBS variable.
                   1582:             *
                   1583:             * If it was .NULL, the source is the suffix to use when a file
                   1584:             * has no valid suffix.
1.75      tv       1585:             *
                   1586:             * If it was .OBJDIR, the source is a new definition for .OBJDIR,
                   1587:             * and will cause make to do a new chdir to that path.
1.1       cgd      1588:             */
1.290     rillig   1589:            while (*cp && !ch_isspace(*cp)) {
1.1       cgd      1590:                cp++;
1.203     joerg    1591:            }
1.1       cgd      1592:            savec = *cp;
                   1593:            *cp = '\0';
                   1594:            switch (specType) {
                   1595:                case Suffixes:
1.203     joerg    1596:                    Suff_AddSuffix(line, &mainNode);
1.1       cgd      1597:                    break;
1.5       cgd      1598:                case ExPath:
1.265     rillig   1599:                    if (paths != NULL)
1.268     rillig   1600:                        Lst_ForEach(paths, ParseAddDir, line);
1.1       cgd      1601:                    break;
                   1602:                case Includes:
1.97      christos 1603:                    Suff_AddInclude(line);
1.1       cgd      1604:                    break;
                   1605:                case Libs:
1.97      christos 1606:                    Suff_AddLib(line);
1.1       cgd      1607:                    break;
                   1608:                case Null:
1.97      christos 1609:                    Suff_SetNull(line);
1.75      tv       1610:                    break;
                   1611:                case ExObjdir:
1.216     christos 1612:                    Main_SetObjdir("%s", line);
1.1       cgd      1613:                    break;
1.5       cgd      1614:                default:
                   1615:                    break;
1.1       cgd      1616:            }
                   1617:            *cp = savec;
1.203     joerg    1618:            if (savec != '\0') {
                   1619:                cp++;
                   1620:            }
1.290     rillig   1621:            while (*cp && ch_isspace(*cp)) {
1.1       cgd      1622:                cp++;
1.203     joerg    1623:            }
                   1624:            line = cp;
1.1       cgd      1625:        }
                   1626:        if (paths) {
1.268     rillig   1627:            Lst_Free(paths);
1.222     riastrad 1628:            paths = NULL;
1.1       cgd      1629:        }
1.85      sjg      1630:        if (specType == ExPath)
                   1631:            Dir_SetPATH();
1.1       cgd      1632:     } else {
1.222     riastrad 1633:        assert(paths == NULL);
1.1       cgd      1634:        while (*line) {
                   1635:            /*
                   1636:             * The targets take real sources, so we must beware of archive
                   1637:             * specifications (i.e. things with left parentheses in them)
                   1638:             * and handle them accordingly.
                   1639:             */
1.290     rillig   1640:            for (; *cp && !ch_isspace(*cp); cp++) {
1.242     rillig   1641:                if (*cp == LPAREN && cp > line && cp[-1] != '$') {
1.1       cgd      1642:                    /*
                   1643:                     * Only stop for a left parenthesis if it isn't at the
                   1644:                     * start of a word (that'll be for variable changes
                   1645:                     * later) and isn't preceded by a dollar sign (a dynamic
                   1646:                     * source).
                   1647:                     */
                   1648:                    break;
                   1649:                }
                   1650:            }
                   1651:
1.77      christos 1652:            if (*cp == LPAREN) {
1.252     rillig   1653:                sources = Lst_Init();
1.264     rillig   1654:                if (!Arch_ParseArchive(&line, sources, VAR_CMD)) {
1.97      christos 1655:                    Parse_Error(PARSE_FATAL,
1.1       cgd      1656:                                 "Error in source archive spec \"%s\"", line);
1.112     christos 1657:                    goto out;
1.1       cgd      1658:                }
                   1659:
1.268     rillig   1660:                while (!Lst_IsEmpty(sources)) {
                   1661:                    gn = Lst_Dequeue(sources);
1.120     dsl      1662:                    ParseDoSrc(tOp, gn->name);
1.1       cgd      1663:                }
1.268     rillig   1664:                Lst_Free(sources);
1.1       cgd      1665:                cp = line;
                   1666:            } else {
                   1667:                if (*cp) {
                   1668:                    *cp = '\0';
                   1669:                    cp += 1;
                   1670:                }
                   1671:
1.120     dsl      1672:                ParseDoSrc(tOp, line);
1.1       cgd      1673:            }
1.290     rillig   1674:            while (*cp && ch_isspace(*cp)) {
1.1       cgd      1675:                cp++;
                   1676:            }
                   1677:            line = cp;
                   1678:        }
                   1679:     }
1.27      christos 1680:
1.265     rillig   1681:     if (mainNode == NULL && targets != NULL) {
1.1       cgd      1682:        /*
                   1683:         * If we have yet to decide on a main target to make, in the
                   1684:         * absence of any user input, we want the first target on
                   1685:         * the first dependency line that is actually a real target
                   1686:         * (i.e. isn't a .USE or .EXEC rule) to be made.
                   1687:         */
1.268     rillig   1688:        Lst_ForEach(targets, ParseFindMain, NULL);
1.1       cgd      1689:     }
                   1690:
1.112     christos 1691: out:
1.263     rillig   1692:     if (paths != NULL)
1.268     rillig   1693:        Lst_Free(paths);
1.263     rillig   1694:     if (curTargs != NULL)
1.268     rillig   1695:        Lst_Free(curTargs);
1.1       cgd      1696: }
                   1697:
                   1698: /*-
                   1699:  *---------------------------------------------------------------------
                   1700:  * Parse_IsVar  --
                   1701:  *     Return TRUE if the passed line is a variable assignment. A variable
                   1702:  *     assignment consists of a single word followed by optional whitespace
                   1703:  *     followed by either a += or an = operator.
                   1704:  *     This function is used both by the Parse_File function and main when
                   1705:  *     parsing the command-line arguments.
                   1706:  *
1.84      wiz      1707:  * Input:
                   1708:  *     line            the line to check
                   1709:  *
1.1       cgd      1710:  * Results:
                   1711:  *     TRUE if it is. FALSE if it ain't
                   1712:  *
                   1713:  * Side Effects:
                   1714:  *     none
                   1715:  *---------------------------------------------------------------------
                   1716:  */
                   1717: Boolean
1.286     rillig   1718: Parse_IsVar(const char *line)
1.1       cgd      1719: {
1.84      wiz      1720:     Boolean wasSpace = FALSE;  /* set TRUE if found a space */
1.154     dsl      1721:     char ch;
1.16      christos 1722:     int level = 0;
                   1723: #define ISEQOPERATOR(c) \
                   1724:        (((c) == '+') || ((c) == ':') || ((c) == '?') || ((c) == '!'))
1.1       cgd      1725:
                   1726:     /*
                   1727:      * Skip to variable name
                   1728:      */
1.242     rillig   1729:     while (*line == ' ' || *line == '\t')
                   1730:        line++;
1.1       cgd      1731:
1.154     dsl      1732:     /* Scan for one of the assignment operators outside a variable expansion */
                   1733:     while ((ch = *line++) != 0) {
                   1734:        if (ch == '(' || ch == '{') {
1.16      christos 1735:            level++;
1.154     dsl      1736:            continue;
                   1737:        }
                   1738:        if (ch == ')' || ch == '}') {
1.16      christos 1739:            level--;
1.154     dsl      1740:            continue;
                   1741:        }
                   1742:        if (level != 0)
                   1743:            continue;
                   1744:        while (ch == ' ' || ch == '\t') {
                   1745:            ch = *line++;
                   1746:            wasSpace = TRUE;
1.1       cgd      1747:        }
1.191     sjg      1748: #ifdef SUNSHCMD
                   1749:        if (ch == ':' && strncmp(line, "sh", 2) == 0) {
                   1750:            line += 2;
                   1751:            continue;
                   1752:        }
                   1753: #endif
1.154     dsl      1754:        if (ch == '=')
                   1755:            return TRUE;
                   1756:        if (*line == '=' && ISEQOPERATOR(ch))
                   1757:            return TRUE;
                   1758:        if (wasSpace)
                   1759:            return FALSE;
                   1760:     }
1.1       cgd      1761:
1.154     dsl      1762:     return FALSE;
1.1       cgd      1763: }
                   1764:
                   1765: /*-
                   1766:  *---------------------------------------------------------------------
                   1767:  * Parse_DoVar  --
                   1768:  *     Take the variable assignment in the passed line and do it in the
                   1769:  *     global context.
                   1770:  *
                   1771:  *     Note: There is a lexical ambiguity with assignment modifier characters
                   1772:  *     in variable names. This routine interprets the character before the =
                   1773:  *     as a modifier. Therefore, an assignment like
                   1774:  *         C++=/usr/bin/CC
                   1775:  *     is interpreted as "C+ +=" instead of "C++ =".
                   1776:  *
1.84      wiz      1777:  * Input:
                   1778:  *     line            a line guaranteed to be a variable assignment.
                   1779:  *                     This reduces error checks
                   1780:  *     ctxt            Context in which to do the assignment
                   1781:  *
1.1       cgd      1782:  * Results:
                   1783:  *     none
                   1784:  *
                   1785:  * Side Effects:
                   1786:  *     the variable structure of the given variable name is altered in the
                   1787:  *     global context.
                   1788:  *---------------------------------------------------------------------
                   1789:  */
                   1790: void
1.84      wiz      1791: Parse_DoVar(char *line, GNode *ctxt)
1.1       cgd      1792: {
1.7       cgd      1793:     char          *cp; /* pointer into line */
1.1       cgd      1794:     enum {
                   1795:        VAR_SUBST, VAR_APPEND, VAR_SHELL, VAR_NORMAL
                   1796:     }              type;       /* Type of assignment */
1.27      christos 1797:     char            *opc;      /* ptr to operator character to
1.1       cgd      1798:                                 * null-terminate the variable name */
1.86      sjg      1799:     Boolean       freeCp = FALSE; /* TRUE if cp needs to be freed,
                   1800:                                    * i.e. if any variable expansion was
                   1801:                                    * performed */
1.153     dsl      1802:     int depth;
1.1       cgd      1803:
                   1804:     /*
                   1805:      * Skip to variable name
                   1806:      */
1.242     rillig   1807:     while (*line == ' ' || *line == '\t')
1.1       cgd      1808:        line++;
                   1809:
                   1810:     /*
                   1811:      * Skip to operator character, nulling out whitespace as we go
1.153     dsl      1812:      * XXX Rather than counting () and {} we should look for $ and
                   1813:      * then expand the variable.
1.1       cgd      1814:      */
1.259     rillig   1815:     for (depth = 0, cp = line; depth > 0 || *cp != '='; cp++) {
1.153     dsl      1816:        if (*cp == '(' || *cp == '{') {
                   1817:            depth++;
                   1818:            continue;
                   1819:        }
                   1820:        if (*cp == ')' || *cp == '}') {
                   1821:            depth--;
                   1822:            continue;
                   1823:        }
1.290     rillig   1824:        if (depth == 0 && ch_isspace(*cp)) {
1.1       cgd      1825:            *cp = '\0';
                   1826:        }
                   1827:     }
                   1828:     opc = cp-1;                /* operator is the previous character */
                   1829:     *cp++ = '\0';      /* nuke the = */
                   1830:
                   1831:     /*
                   1832:      * Check operator type
                   1833:      */
                   1834:     switch (*opc) {
                   1835:        case '+':
                   1836:            type = VAR_APPEND;
                   1837:            *opc = '\0';
                   1838:            break;
                   1839:
                   1840:        case '?':
                   1841:            /*
                   1842:             * If the variable already has a value, we don't do anything.
                   1843:             */
                   1844:            *opc = '\0';
                   1845:            if (Var_Exists(line, ctxt)) {
                   1846:                return;
                   1847:            } else {
                   1848:                type = VAR_NORMAL;
                   1849:            }
                   1850:            break;
                   1851:
                   1852:        case ':':
                   1853:            type = VAR_SUBST;
                   1854:            *opc = '\0';
                   1855:            break;
                   1856:
                   1857:        case '!':
                   1858:            type = VAR_SHELL;
                   1859:            *opc = '\0';
                   1860:            break;
                   1861:
                   1862:        default:
1.23      christos 1863: #ifdef SUNSHCMD
1.39      christos 1864:            while (opc > line && *opc != ':')
                   1865:                opc--;
1.23      christos 1866:
                   1867:            if (strncmp(opc, ":sh", 3) == 0) {
                   1868:                type = VAR_SHELL;
                   1869:                *opc = '\0';
                   1870:                break;
                   1871:            }
                   1872: #endif
1.1       cgd      1873:            type = VAR_NORMAL;
                   1874:            break;
                   1875:     }
                   1876:
1.290     rillig   1877:     while (ch_isspace(*cp))
1.1       cgd      1878:        cp++;
                   1879:
1.243     sjg      1880:     if (DEBUG(LINT)) {
                   1881:        if (type != VAR_SUBST && strchr(cp, '$') != NULL) {
                   1882:            /* sanity check now */
                   1883:            char *cp2;
                   1884:
1.249     sjg      1885:            cp2 = Var_Subst(cp, ctxt, VARE_ASSIGN);
1.243     sjg      1886:            free(cp2);
                   1887:        }
                   1888:     }
                   1889:
1.1       cgd      1890:     if (type == VAR_APPEND) {
1.97      christos 1891:        Var_Append(line, cp, ctxt);
1.1       cgd      1892:     } else if (type == VAR_SUBST) {
                   1893:        /*
                   1894:         * Allow variables in the old value to be undefined, but leave their
1.295     rillig   1895:         * expressions alone -- this is done by forcing oldVars to be false.
1.1       cgd      1896:         * XXX: This can cause recursive variables, but that's not hard to do,
                   1897:         * and this allows someone to do something like
                   1898:         *
                   1899:         *  CFLAGS = $(.INCLUDES)
                   1900:         *  CFLAGS := -I.. $(CFLAGS)
                   1901:         *
                   1902:         * And not get an error.
                   1903:         */
                   1904:        Boolean   oldOldVars = oldVars;
                   1905:
                   1906:        oldVars = FALSE;
1.42      christos 1907:
                   1908:        /*
                   1909:         * make sure that we set the variable the first time to nothing
                   1910:         * so that it gets substituted!
                   1911:         */
                   1912:        if (!Var_Exists(line, ctxt))
1.234     rillig   1913:            Var_Set(line, "", ctxt);
1.42      christos 1914:
1.239     rillig   1915:        cp = Var_Subst(cp, ctxt, VARE_WANTRES|VARE_ASSIGN);
1.1       cgd      1916:        oldVars = oldOldVars;
1.86      sjg      1917:        freeCp = TRUE;
1.1       cgd      1918:
1.234     rillig   1919:        Var_Set(line, cp, ctxt);
1.1       cgd      1920:     } else if (type == VAR_SHELL) {
1.93      christos 1921:        char *res;
1.115     christos 1922:        const char *error;
1.5       cgd      1923:
1.23      christos 1924:        if (strchr(cp, '$') != NULL) {
1.1       cgd      1925:            /*
                   1926:             * There's a dollar sign in the command, so perform variable
                   1927:             * expansion on the whole thing. The resulting string will need
1.238     rillig   1928:             * freeing when we're done.
1.1       cgd      1929:             */
1.239     rillig   1930:            cp = Var_Subst(cp, VAR_CMD, VARE_UNDEFERR|VARE_WANTRES);
1.86      sjg      1931:            freeCp = TRUE;
1.1       cgd      1932:        }
                   1933:
1.115     christos 1934:        res = Cmd_Exec(cp, &error);
1.234     rillig   1935:        Var_Set(line, res, ctxt);
1.23      christos 1936:        free(res);
1.1       cgd      1937:
1.115     christos 1938:        if (error)
                   1939:            Parse_Error(PARSE_WARNING, error, cp);
1.1       cgd      1940:     } else {
                   1941:        /*
                   1942:         * Normal assignment -- just do it.
                   1943:         */
1.234     rillig   1944:        Var_Set(line, cp, ctxt);
1.1       cgd      1945:     }
1.69      sjg      1946:     if (strcmp(line, MAKEOVERRIDES) == 0)
1.74      tv       1947:        Main_ExportMAKEFLAGS(FALSE);    /* re-export MAKEFLAGS */
1.85      sjg      1948:     else if (strcmp(line, ".CURDIR") == 0) {
                   1949:        /*
                   1950:         * Somone is being (too?) clever...
                   1951:         * Let's pretend they know what they are doing and
                   1952:         * re-initialize the 'cur' Path.
                   1953:         */
                   1954:        Dir_InitCur(cp);
                   1955:        Dir_SetPATH();
1.136     sjg      1956:     } else if (strcmp(line, MAKE_JOB_PREFIX) == 0) {
1.135     sjg      1957:        Job_SetPrefix();
1.136     sjg      1958:     } else if (strcmp(line, MAKE_EXPORTED) == 0) {
1.250     rillig   1959:        Var_Export(cp, FALSE);
1.85      sjg      1960:     }
1.86      sjg      1961:     if (freeCp)
                   1962:        free(cp);
1.1       cgd      1963: }
1.23      christos 1964:
1.200     christos 1965:
1.203     joerg    1966: /*
1.195     christos 1967:  * ParseMaybeSubMake --
                   1968:  *     Scan the command string to see if it a possible submake node
                   1969:  * Input:
                   1970:  *     cmd             the command to scan
                   1971:  * Results:
                   1972:  *     TRUE if the command is possibly a submake, FALSE if not.
                   1973:  */
                   1974: static Boolean
                   1975: ParseMaybeSubMake(const char *cmd)
                   1976: {
1.197     justin   1977:     size_t i;
1.195     christos 1978:     static struct {
                   1979:        const char *name;
                   1980:        size_t len;
                   1981:     } vals[] = {
                   1982: #define MKV(A) {       A, sizeof(A) - 1        }
                   1983:        MKV("${MAKE}"),
                   1984:        MKV("${.MAKE}"),
                   1985:        MKV("$(MAKE)"),
                   1986:        MKV("$(.MAKE)"),
                   1987:        MKV("make"),
                   1988:     };
1.198     justin   1989:     for (i = 0; i < sizeof(vals)/sizeof(vals[0]); i++) {
1.195     christos 1990:        char *ptr;
                   1991:        if ((ptr = strstr(cmd, vals[i].name)) == NULL)
                   1992:            continue;
1.290     rillig   1993:        if ((ptr == cmd || !ch_isalnum(ptr[-1]))
                   1994:            && !ch_isalnum(ptr[vals[i].len]))
1.195     christos 1995:            return TRUE;
                   1996:     }
                   1997:     return FALSE;
                   1998: }
                   1999:
1.1       cgd      2000: /*-
                   2001:  * ParseAddCmd  --
                   2002:  *     Lst_ForEach function to add a command line to all targets
                   2003:  *
1.84      wiz      2004:  * Input:
                   2005:  *     gnp             the node to which the command is to be added
                   2006:  *     cmd             the command to add
                   2007:  *
1.1       cgd      2008:  * Results:
                   2009:  *     Always 0
                   2010:  *
                   2011:  * Side Effects:
1.195     christos 2012:  *     A new element is added to the commands list of the node,
                   2013:  *     and the node can be marked as a submake node if the command is
                   2014:  *     determined to be that.
1.1       cgd      2015:  */
1.5       cgd      2016: static int
1.157     dsl      2017: ParseAddCmd(void *gnp, void *cmd)
1.9       jtc      2018: {
1.105     christos 2019:     GNode *gn = (GNode *)gnp;
1.120     dsl      2020:
                   2021:     /* Add to last (ie current) cohort for :: targets */
1.268     rillig   2022:     if ((gn->type & OP_DOUBLEDEP) && !Lst_IsEmpty(gn->cohorts))
1.274     rillig   2023:        gn = LstNode_Datum(Lst_Last(gn->cohorts));
1.120     dsl      2024:
1.203     joerg    2025:     /* if target already supplied, ignore commands */
                   2026:     if (!(gn->type & OP_HAS_COMMANDS)) {
1.268     rillig   2027:        Lst_Append(gn->commands, cmd);
1.203     joerg    2028:        if (ParseMaybeSubMake(cmd))
                   2029:            gn->type |= OP_SUBMAKE;
                   2030:        ParseMark(gn);
                   2031:     } else {
                   2032: #ifdef notyet
                   2033:        /* XXX: We cannot do this until we fix the tree */
1.268     rillig   2034:        Lst_Append(gn->commands, cmd);
1.203     joerg    2035:        Parse_Error(PARSE_WARNING,
                   2036:                     "overriding commands for target \"%s\"; "
                   2037:                     "previous commands defined at %s: %d ignored",
                   2038:                     gn->name, gn->fname, gn->lineno);
                   2039: #else
                   2040:        Parse_Error(PARSE_WARNING,
                   2041:                     "duplicate script for target \"%s\" ignored",
                   2042:                     gn->name);
                   2043:        ParseErrorInternal(gn->fname, gn->lineno, PARSE_WARNING,
                   2044:                            "using previous script for \"%s\" defined here",
                   2045:                            gn->name);
                   2046: #endif
1.200     christos 2047:     }
1.235     rillig   2048:     return 0;
1.1       cgd      2049: }
                   2050:
1.284     rillig   2051: /* Callback procedure for Parse_File when destroying the list of targets on
                   2052:  * the last dependency line. Marks a target as already having commands if it
                   2053:  * does, to keep from having shell commands on multiple dependency lines. */
1.9       jtc      2054: static void
1.157     dsl      2055: ParseHasCommands(void *gnp)
1.1       cgd      2056: {
1.105     christos 2057:     GNode *gn = (GNode *)gnp;
1.268     rillig   2058:     if (!Lst_IsEmpty(gn->commands)) {
1.1       cgd      2059:        gn->type |= OP_HAS_COMMANDS;
                   2060:     }
                   2061: }
                   2062:
1.284     rillig   2063: /* Add a directory to the path searched for included makefiles bracketed
                   2064:  * by double-quotes. */
1.1       cgd      2065: void
1.84      wiz      2066: Parse_AddIncludeDir(char *dir)
1.1       cgd      2067: {
1.103     christos 2068:     (void)Dir_AddDir(parseIncPath, dir);
1.1       cgd      2069: }
                   2070:
1.284     rillig   2071: /* Push to another file.
1.1       cgd      2072:  *
1.284     rillig   2073:  * The input is the line minus the '.'. A file spec is a string enclosed in
                   2074:  * <> or "". The <> file is looked for only in sysIncPath. The "" file is
                   2075:  * first searched in the parsedir and then in the directories specified by
                   2076:  * the -I command line options.
1.1       cgd      2077:  */
                   2078: static void
1.210     sjg      2079: Parse_include_file(char *file, Boolean isSystem, Boolean depinc, int silent)
1.1       cgd      2080: {
1.170     dholland 2081:     struct loadedfile *lf;
1.1       cgd      2082:     char          *fullname;   /* full pathname of file */
1.140     dsl      2083:     char          *newName;
                   2084:     char          *prefEnd, *incdir;
1.125     dsl      2085:     int           fd;
1.140     dsl      2086:     int           i;
1.1       cgd      2087:
                   2088:     /*
                   2089:      * Now we know the file's name and its search path, we attempt to
                   2090:      * find the durn thing. A return of NULL indicates the file don't
                   2091:      * exist.
                   2092:      */
1.147     joerg    2093:     fullname = file[0] == '/' ? bmake_strdup(file) : NULL;
1.76      reinoud  2094:
1.140     dsl      2095:     if (fullname == NULL && !isSystem) {
1.1       cgd      2096:        /*
                   2097:         * Include files contained in double-quotes are first searched for
                   2098:         * relative to the including file's location. We don't want to
                   2099:         * cd there, of course, so we just tack on the old file's
                   2100:         * leading path components and call Dir_FindFile to see if
                   2101:         * we can locate the beast.
                   2102:         */
                   2103:
1.147     joerg    2104:        incdir = bmake_strdup(curFile->fname);
1.140     dsl      2105:        prefEnd = strrchr(incdir, '/');
1.105     christos 2106:        if (prefEnd != NULL) {
1.1       cgd      2107:            *prefEnd = '\0';
1.140     dsl      2108:            /* Now do lexical processing of leading "../" on the filename */
                   2109:            for (i = 0; strncmp(file + i, "../", 3) == 0; i += 3) {
                   2110:                prefEnd = strrchr(incdir + 1, '/');
                   2111:                if (prefEnd == NULL || strcmp(prefEnd, "/..") == 0)
                   2112:                    break;
                   2113:                *prefEnd = '\0';
                   2114:            }
1.251     rillig   2115:            newName = str_concat3(incdir, "/", file + i);
1.97      christos 2116:            fullname = Dir_FindFile(newName, parseIncPath);
1.140     dsl      2117:            if (fullname == NULL)
1.1       cgd      2118:                fullname = Dir_FindFile(newName, dirSearchPath);
1.103     christos 2119:            free(newName);
1.1       cgd      2120:        }
1.140     dsl      2121:        free(incdir);
                   2122:
1.142     sjg      2123:        if (fullname == NULL) {
1.76      reinoud  2124:            /*
1.246     rillig   2125:             * Makefile wasn't found in same directory as included makefile.
1.76      reinoud  2126:             * Search for it first on the -I search path,
                   2127:             * then on the .PATH search path, if not found in a -I directory.
1.142     sjg      2128:             * If we have a suffix specific path we should use that.
1.76      reinoud  2129:             */
1.142     sjg      2130:            char *suff;
1.152     dsl      2131:            Lst suffPath = NULL;
1.142     sjg      2132:
1.145     christos 2133:            if ((suff = strrchr(file, '.'))) {
1.142     sjg      2134:                suffPath = Suff_GetPath(suff);
1.152     dsl      2135:                if (suffPath != NULL) {
1.142     sjg      2136:                    fullname = Dir_FindFile(file, suffPath);
                   2137:                }
                   2138:            }
1.105     christos 2139:            if (fullname == NULL) {
1.142     sjg      2140:                fullname = Dir_FindFile(file, parseIncPath);
                   2141:                if (fullname == NULL) {
                   2142:                    fullname = Dir_FindFile(file, dirSearchPath);
                   2143:                }
1.76      reinoud  2144:            }
1.142     sjg      2145:        }
1.1       cgd      2146:     }
                   2147:
1.76      reinoud  2148:     /* Looking for a system file or file still not found */
1.105     christos 2149:     if (fullname == NULL) {
1.1       cgd      2150:        /*
1.76      reinoud  2151:         * Look for it on the system path
1.1       cgd      2152:         */
1.123     dsl      2153:        fullname = Dir_FindFile(file,
1.268     rillig   2154:                    Lst_IsEmpty(sysIncPath) ? defIncPath : sysIncPath);
1.1       cgd      2155:     }
                   2156:
1.105     christos 2157:     if (fullname == NULL) {
1.38      christos 2158:        if (!silent)
1.97      christos 2159:            Parse_Error(PARSE_FATAL, "Could not find %s", file);
1.1       cgd      2160:        return;
                   2161:     }
                   2162:
1.125     dsl      2163:     /* Actually open the file... */
                   2164:     fd = open(fullname, O_RDONLY);
                   2165:     if (fd == -1) {
1.38      christos 2166:        if (!silent)
1.97      christos 2167:            Parse_Error(PARSE_FATAL, "Cannot open %s", fullname);
1.140     dsl      2168:        free(fullname);
1.125     dsl      2169:        return;
1.123     dsl      2170:     }
1.125     dsl      2171:
1.170     dholland 2172:     /* load it */
                   2173:     lf = loadfile(fullname, fd);
                   2174:
1.125     dsl      2175:     /* Start reading from this file next */
1.170     dholland 2176:     Parse_SetInput(fullname, 0, -1, loadedfile_nextbuf, lf);
                   2177:     curFile->lf = lf;
1.210     sjg      2178:     if (depinc)
                   2179:        doing_depend = depinc;          /* only turn it on */
1.123     dsl      2180: }
                   2181:
                   2182: static void
                   2183: ParseDoInclude(char *line)
                   2184: {
                   2185:     char          endc;                /* the character which ends the file spec */
                   2186:     char          *cp;         /* current position in file spec */
1.242     rillig   2187:     int                  silent = *line != 'i';
1.123     dsl      2188:     char         *file = &line[7 + silent];
                   2189:
                   2190:     /* Skip to delimiter character so we know where to look */
                   2191:     while (*file == ' ' || *file == '\t')
                   2192:        file++;
                   2193:
                   2194:     if (*file != '"' && *file != '<') {
                   2195:        Parse_Error(PARSE_FATAL,
                   2196:            ".include filename must be delimited by '\"' or '<'");
                   2197:        return;
                   2198:     }
                   2199:
                   2200:     /*
                   2201:      * Set the search path on which to find the include file based on the
                   2202:      * characters which bracket its name. Angle-brackets imply it's
                   2203:      * a system Makefile while double-quotes imply it's a user makefile
                   2204:      */
                   2205:     if (*file == '<') {
                   2206:        endc = '>';
                   2207:     } else {
                   2208:        endc = '"';
                   2209:     }
                   2210:
                   2211:     /* Skip to matching delimiter */
                   2212:     for (cp = ++file; *cp && *cp != endc; cp++)
                   2213:        continue;
                   2214:
                   2215:     if (*cp != endc) {
                   2216:        Parse_Error(PARSE_FATAL,
                   2217:                     "Unclosed %cinclude filename. '%c' expected",
                   2218:                     '.', endc);
                   2219:        return;
1.1       cgd      2220:     }
1.123     dsl      2221:     *cp = '\0';
                   2222:
                   2223:     /*
                   2224:      * Substitute for any variables in the file name before trying to
                   2225:      * find the thing.
                   2226:      */
1.239     rillig   2227:     file = Var_Subst(file, VAR_CMD, VARE_WANTRES);
1.123     dsl      2228:
1.242     rillig   2229:     Parse_include_file(file, endc == '>', *line == 'd', silent);
1.123     dsl      2230:     free(file);
1.1       cgd      2231: }
                   2232:
1.281     rillig   2233: /* Split filename into dirname + basename, then assign these to the
                   2234:  * given variables. */
1.193     christos 2235: static void
1.281     rillig   2236: SetFilenameVars(const char *filename, const char *dirvar, const char *filevar)
1.193     christos 2237: {
1.281     rillig   2238:     const char *slash, *dirname, *basename;
                   2239:     void *freeIt;
                   2240:
                   2241:     slash = strrchr(filename, '/');
                   2242:     if (slash == NULL) {
                   2243:        dirname = curdir;
                   2244:        basename = filename;
                   2245:        freeIt = NULL;
                   2246:     } else {
                   2247:        dirname = freeIt = bmake_strsedup(filename, slash);
                   2248:        basename = slash + 1;
                   2249:     }
1.193     christos 2250:
1.281     rillig   2251:     Var_Set(dirvar, dirname, VAR_GLOBAL);
                   2252:     Var_Set(filevar, basename, VAR_GLOBAL);
1.193     christos 2253:
                   2254:     if (DEBUG(PARSE))
1.281     rillig   2255:        fprintf(debug_file, "%s: ${%s} = `%s' ${%s} = `%s'\n",
                   2256:                __func__, dirvar, dirname, filevar, basename);
                   2257:     free(freeIt);
                   2258: }
                   2259:
                   2260: /* Return the immediately including file.
                   2261:  *
                   2262:  * This is made complicated since the .for loop is implemented as a special
                   2263:  * kind of .include; see For_Run. */
                   2264: static const char *
                   2265: GetActuallyIncludingFile(void)
                   2266: {
                   2267:     size_t i;
1.193     christos 2268:
1.281     rillig   2269:     /* XXX: Stack was supposed to be an opaque data structure. */
1.282     rillig   2270:     for (i = includes.len; i > 0; i--) {
                   2271:        IFile *parent = includes.items[i - 1];
1.284     rillig   2272:        IFile *child = i < includes.len ? includes.items[i] : curFile;
1.281     rillig   2273:        if (!child->fromForLoop)
1.282     rillig   2274:            return parent->fname;
1.281     rillig   2275:     }
1.282     rillig   2276:     return NULL;
1.193     christos 2277: }
1.281     rillig   2278:
1.285     rillig   2279: /* Set .PARSEDIR, .PARSEFILE, .INCLUDEDFROMDIR and .INCLUDEDFROMFILE. */
1.44      aidan    2280: static void
1.122     dsl      2281: ParseSetParseFile(const char *filename)
1.44      aidan    2282: {
1.281     rillig   2283:     const char *including;
1.44      aidan    2284:
1.281     rillig   2285:     SetFilenameVars(filename, ".PARSEDIR", ".PARSEFILE");
                   2286:
                   2287:     including = GetActuallyIncludingFile();
                   2288:     if (including != NULL) {
                   2289:        SetFilenameVars(including,
                   2290:                        ".INCLUDEDFROMDIR", ".INCLUDEDFROMFILE");
1.44      aidan    2291:     } else {
1.281     rillig   2292:        Var_Delete(".INCLUDEDFROMDIR", VAR_GLOBAL);
                   2293:        Var_Delete(".INCLUDEDFROMFILE", VAR_GLOBAL);
1.44      aidan    2294:     }
                   2295: }
                   2296:
1.284     rillig   2297: /* Track the makefiles we read - so makefiles can set dependencies on them.
                   2298:  * Avoid adding anything more than once. */
1.184     sjg      2299: static void
                   2300: ParseTrackInput(const char *name)
                   2301: {
                   2302:     char *fp = NULL;
1.236     rillig   2303:
1.244     rillig   2304:     const char *old = Var_Value(MAKE_MAKEFILES, VAR_GLOBAL, &fp);
1.184     sjg      2305:     if (old) {
1.244     rillig   2306:        size_t name_len = strlen(name);
                   2307:        const char *ep = old + strlen(old) - name_len;
1.184     sjg      2308:        /* does it contain name? */
                   2309:        for (; old != NULL; old = strchr(old, ' ')) {
                   2310:            if (*old == ' ')
                   2311:                old++;
1.206     sjg      2312:            if (old >= ep)
                   2313:                break;                  /* cannot contain name */
1.184     sjg      2314:            if (memcmp(old, name, name_len) == 0
                   2315:                    && (old[name_len] == 0 || old[name_len] == ' '))
                   2316:                goto cleanup;
                   2317:        }
                   2318:     }
                   2319:     Var_Append (MAKE_MAKEFILES, name, VAR_GLOBAL);
                   2320:  cleanup:
1.245     rillig   2321:     bmake_free(fp);
1.184     sjg      2322: }
1.137     sjg      2323:
1.44      aidan    2324:
1.276     rillig   2325: /* Start Parsing from the given source.
1.5       cgd      2326:  *
1.276     rillig   2327:  * The given file is added to the includes stack. */
1.5       cgd      2328: void
1.170     dholland 2329: Parse_SetInput(const char *name, int line, int fd,
                   2330:        char *(*nextbuf)(void *, size_t *), void *arg)
1.5       cgd      2331: {
1.155     dsl      2332:     char *buf;
1.170     dholland 2333:     size_t len;
1.281     rillig   2334:     Boolean fromForLoop = name == NULL;
1.155     dsl      2335:
1.281     rillig   2336:     if (fromForLoop)
1.127     dsl      2337:        name = curFile->fname;
1.139     dsl      2338:     else
1.184     sjg      2339:        ParseTrackInput(name);
1.127     dsl      2340:
                   2341:     if (DEBUG(PARSE))
1.288     rillig   2342:        fprintf(debug_file, "%s: file %s, line %d, fd %d, nextbuf %s, arg %p\n",
                   2343:                __func__, name, line, fd,
                   2344:                nextbuf == loadedfile_nextbuf ? "loadedfile" : "other", arg);
1.127     dsl      2345:
1.155     dsl      2346:     if (fd == -1 && nextbuf == NULL)
1.125     dsl      2347:        /* sanity */
                   2348:        return;
                   2349:
1.132     dsl      2350:     if (curFile != NULL)
1.281     rillig   2351:        /* Save existing file info */
1.276     rillig   2352:        Stack_Push(&includes, curFile);
1.5       cgd      2353:
1.125     dsl      2354:     /* Allocate and fill in new structure */
1.147     joerg    2355:     curFile = bmake_malloc(sizeof *curFile);
1.125     dsl      2356:
                   2357:     /*
                   2358:      * Once the previous state has been saved, we can get down to reading
                   2359:      * the new file. We set up the name of the file to be the absolute
                   2360:      * name of the include file so error messages refer to the right
                   2361:      * place.
                   2362:      */
1.189     sjg      2363:     curFile->fname = bmake_strdup(name);
1.281     rillig   2364:     curFile->fromForLoop = fromForLoop;
1.125     dsl      2365:     curFile->lineno = line;
1.155     dsl      2366:     curFile->first_lineno = line;
                   2367:     curFile->nextbuf = nextbuf;
                   2368:     curFile->nextbuf_arg = arg;
1.170     dholland 2369:     curFile->lf = NULL;
1.212     sjg      2370:     curFile->depending = doing_depend; /* restore this on EOF */
1.170     dholland 2371:
                   2372:     assert(nextbuf != NULL);
1.125     dsl      2373:
1.170     dholland 2374:     /* Get first block of input data */
                   2375:     buf = curFile->nextbuf(curFile->nextbuf_arg, &len);
                   2376:     if (buf == NULL) {
1.246     rillig   2377:        /* Was all a waste of time ... */
1.189     sjg      2378:        if (curFile->fname)
                   2379:            free(curFile->fname);
1.170     dholland 2380:        free(curFile);
                   2381:        return;
1.125     dsl      2382:     }
1.170     dholland 2383:     curFile->P_str = buf;
                   2384:     curFile->P_ptr = buf;
                   2385:     curFile->P_end = buf+len;
1.5       cgd      2386:
1.155     dsl      2387:     curFile->cond_depth = Cond_save_depth();
                   2388:     ParseSetParseFile(name);
1.5       cgd      2389: }
                   2390:
1.284     rillig   2391: /* Check if the line is an include directive. */
1.228     christos 2392: static Boolean
1.298     rillig   2393: IsInclude(const char *dir, Boolean sysv)
1.228     christos 2394: {
1.298     rillig   2395:        if (dir[0] == 's' || dir[0] == '-' || (dir[0] == 'd' && !sysv))
                   2396:                dir++;
1.228     christos 2397:
1.298     rillig   2398:        if (strncmp(dir, "include", 7) != 0)
1.228     christos 2399:                return FALSE;
                   2400:
1.248     rillig   2401:        /* Space is not mandatory for BSD .include */
1.298     rillig   2402:        return !sysv || ch_isspace(dir[7]);
1.228     christos 2403: }
                   2404:
                   2405:
1.5       cgd      2406: #ifdef SYSVINCLUDE
1.284     rillig   2407: /* Check if the line is a SYSV include directive. */
1.228     christos 2408: static Boolean
                   2409: IsSysVInclude(const char *line)
                   2410: {
                   2411:        const char *p;
                   2412:
                   2413:        if (!IsInclude(line, TRUE))
                   2414:                return FALSE;
                   2415:
                   2416:        /* Avoid interpeting a dependency line as an include */
                   2417:        for (p = line; (p = strchr(p, ':')) != NULL;) {
                   2418:                if (*++p == '\0') {
                   2419:                        /* end of line -> dependency */
                   2420:                        return FALSE;
                   2421:                }
1.290     rillig   2422:                if (*p == ':' || ch_isspace(*p)) {
1.228     christos 2423:                        /* :: operator or ': ' -> dependency */
                   2424:                        return FALSE;
                   2425:                }
                   2426:        }
                   2427:        return TRUE;
                   2428: }
                   2429:
1.284     rillig   2430: /* Push to another file.  The line points to the word "include". */
1.5       cgd      2431: static void
1.84      wiz      2432: ParseTraditionalInclude(char *line)
1.5       cgd      2433: {
                   2434:     char          *cp;         /* current position in file spec */
1.38      christos 2435:     int                   done = 0;
1.242     rillig   2436:     int                   silent = line[0] != 'i';
1.38      christos 2437:     char         *file = &line[silent + 7];
1.123     dsl      2438:     char         *all_files;
1.5       cgd      2439:
1.284     rillig   2440:     if (DEBUG(PARSE))
                   2441:        fprintf(debug_file, "%s: %s\n", __func__, file);
1.111     ginsbach 2442:
1.5       cgd      2443:     /*
                   2444:      * Skip over whitespace
                   2445:      */
1.290     rillig   2446:     while (ch_isspace(*file))
1.5       cgd      2447:        file++;
                   2448:
1.111     ginsbach 2449:     /*
                   2450:      * Substitute for any variables in the file name before trying to
                   2451:      * find the thing.
                   2452:      */
1.239     rillig   2453:     all_files = Var_Subst(file, VAR_CMD, VARE_WANTRES);
1.111     ginsbach 2454:
1.5       cgd      2455:     if (*file == '\0') {
1.97      christos 2456:        Parse_Error(PARSE_FATAL,
1.5       cgd      2457:                     "Filename missing from \"include\"");
1.224     riastrad 2458:        goto out;
1.5       cgd      2459:     }
                   2460:
1.123     dsl      2461:     for (file = all_files; !done; file = cp + 1) {
                   2462:        /* Skip to end of line or next whitespace */
1.290     rillig   2463:        for (cp = file; *cp && !ch_isspace(*cp); cp++)
1.38      christos 2464:            continue;
                   2465:
                   2466:        if (*cp)
                   2467:            *cp = '\0';
                   2468:        else
                   2469:            done = 1;
                   2470:
1.210     sjg      2471:        Parse_include_file(file, FALSE, FALSE, silent);
1.5       cgd      2472:     }
1.224     riastrad 2473: out:
1.123     dsl      2474:     free(all_files);
1.5       cgd      2475: }
                   2476: #endif
                   2477:
1.183     sjg      2478: #ifdef GMAKEEXPORT
1.284     rillig   2479: /* Parse export <variable>=<value>, and actually export it. */
1.182     christos 2480: static void
                   2481: ParseGmakeExport(char *line)
                   2482: {
                   2483:     char         *variable = &line[6];
                   2484:     char         *value;
                   2485:
1.284     rillig   2486:     if (DEBUG(PARSE))
                   2487:        fprintf(debug_file, "%s: %s\n", __func__, variable);
1.182     christos 2488:
                   2489:     /*
                   2490:      * Skip over whitespace
                   2491:      */
1.290     rillig   2492:     while (ch_isspace(*variable))
1.182     christos 2493:        variable++;
                   2494:
                   2495:     for (value = variable; *value && *value != '='; value++)
                   2496:        continue;
                   2497:
                   2498:     if (*value != '=') {
                   2499:        Parse_Error(PARSE_FATAL,
1.284     rillig   2500:                    "Variable/Value missing from \"export\"");
1.182     christos 2501:        return;
                   2502:     }
1.188     sjg      2503:     *value++ = '\0';                   /* terminate variable */
1.182     christos 2504:
                   2505:     /*
1.183     sjg      2506:      * Expand the value before putting it in the environment.
1.182     christos 2507:      */
1.239     rillig   2508:     value = Var_Subst(value, VAR_CMD, VARE_WANTRES);
1.182     christos 2509:     setenv(variable, value, 1);
1.223     riastrad 2510:     free(value);
1.182     christos 2511: }
                   2512: #endif
                   2513:
1.284     rillig   2514: /* Called when EOF is reached in the current file. If we were reading an
                   2515:  * include file, the includes stack is popped and things set up to go back
                   2516:  * to reading the previous file at the previous location.
1.1       cgd      2517:  *
                   2518:  * Results:
                   2519:  *     CONTINUE if there's more to do. DONE if not.
                   2520:  */
                   2521: static int
1.123     dsl      2522: ParseEOF(void)
1.1       cgd      2523: {
1.155     dsl      2524:     char *ptr;
1.170     dholland 2525:     size_t len;
                   2526:
                   2527:     assert(curFile->nextbuf != NULL);
1.155     dsl      2528:
1.210     sjg      2529:     doing_depend = curFile->depending; /* restore this */
1.170     dholland 2530:     /* get next input buffer, if any */
                   2531:     ptr = curFile->nextbuf(curFile->nextbuf_arg, &len);
                   2532:     curFile->P_ptr = ptr;
                   2533:     curFile->P_str = ptr;
                   2534:     curFile->P_end = ptr + len;
                   2535:     curFile->lineno = curFile->first_lineno;
                   2536:     if (ptr != NULL) {
                   2537:        /* Iterate again */
                   2538:        return CONTINUE;
1.155     dsl      2539:     }
                   2540:
1.132     dsl      2541:     /* Ensure the makefile (or loop) didn't have mismatched conditionals */
                   2542:     Cond_restore_depth(curFile->cond_depth);
1.131     dsl      2543:
1.170     dholland 2544:     if (curFile->lf != NULL) {
                   2545:            loadedfile_destroy(curFile->lf);
                   2546:            curFile->lf = NULL;
                   2547:     }
                   2548:
1.125     dsl      2549:     /* Dispose of curFile info */
                   2550:     /* Leak curFile->fname because all the gnodes have pointers to it */
                   2551:     free(curFile->P_str);
                   2552:     free(curFile);
                   2553:
1.276     rillig   2554:     if (Stack_IsEmpty(&includes)) {
1.258     rillig   2555:        curFile = NULL;
1.125     dsl      2556:        /* We've run out of input */
1.44      aidan    2557:        Var_Delete(".PARSEDIR", VAR_GLOBAL);
                   2558:        Var_Delete(".PARSEFILE", VAR_GLOBAL);
1.194     christos 2559:        Var_Delete(".INCLUDEDFROMDIR", VAR_GLOBAL);
                   2560:        Var_Delete(".INCLUDEDFROMFILE", VAR_GLOBAL);
1.125     dsl      2561:        return DONE;
1.1       cgd      2562:     }
                   2563:
1.276     rillig   2564:     curFile = Stack_Pop(&includes);
1.127     dsl      2565:     if (DEBUG(PARSE))
1.170     dholland 2566:        fprintf(debug_file, "ParseEOF: returning to file %s, line %d\n",
                   2567:            curFile->fname, curFile->lineno);
1.127     dsl      2568:
1.125     dsl      2569:     ParseSetParseFile(curFile->fname);
1.235     rillig   2570:     return CONTINUE;
1.1       cgd      2571: }
                   2572:
1.127     dsl      2573: #define PARSE_RAW 1
                   2574: #define PARSE_SKIP 2
                   2575:
                   2576: static char *
                   2577: ParseGetLine(int flags, int *length)
1.5       cgd      2578: {
1.125     dsl      2579:     IFile *cf = curFile;
1.127     dsl      2580:     char *ptr;
1.125     dsl      2581:     char ch;
1.127     dsl      2582:     char *line;
                   2583:     char *line_end;
                   2584:     char *escaped;
                   2585:     char *comment;
                   2586:     char *tp;
1.125     dsl      2587:
1.127     dsl      2588:     /* Loop through blank lines and comment lines */
1.125     dsl      2589:     for (;;) {
1.127     dsl      2590:        cf->lineno++;
                   2591:        line = cf->P_ptr;
                   2592:        ptr = line;
                   2593:        line_end = line;
                   2594:        escaped = NULL;
                   2595:        comment = NULL;
                   2596:        for (;;) {
1.170     dholland 2597:            if (cf->P_end != NULL && ptr == cf->P_end) {
                   2598:                /* end of buffer */
                   2599:                ch = 0;
                   2600:                break;
                   2601:            }
1.127     dsl      2602:            ch = *ptr;
                   2603:            if (ch == 0 || (ch == '\\' && ptr[1] == 0)) {
                   2604:                if (cf->P_end == NULL)
                   2605:                    /* End of string (aka for loop) data */
                   2606:                    break;
1.190     sjg      2607:                /* see if there is more we can parse */
                   2608:                while (ptr++ < cf->P_end) {
                   2609:                    if ((ch = *ptr) == '\n') {
                   2610:                        if (ptr > line && ptr[-1] == '\\')
                   2611:                            continue;
                   2612:                        Parse_Error(PARSE_WARNING,
                   2613:                            "Zero byte read from file, skipping rest of line.");
                   2614:                        break;
                   2615:                    }
                   2616:                }
1.170     dholland 2617:                if (cf->nextbuf != NULL) {
                   2618:                    /*
                   2619:                     * End of this buffer; return EOF and outer logic
                   2620:                     * will get the next one. (eww)
                   2621:                     */
1.127     dsl      2622:                    break;
                   2623:                }
1.170     dholland 2624:                Parse_Error(PARSE_FATAL, "Zero byte read from file");
                   2625:                return NULL;
1.127     dsl      2626:            }
                   2627:
                   2628:            if (ch == '\\') {
                   2629:                /* Don't treat next character as special, remember first one */
                   2630:                if (escaped == NULL)
                   2631:                    escaped = ptr;
                   2632:                if (ptr[1] == '\n')
                   2633:                    cf->lineno++;
                   2634:                ptr += 2;
                   2635:                line_end = ptr;
                   2636:                continue;
                   2637:            }
                   2638:            if (ch == '#' && comment == NULL) {
                   2639:                /* Remember first '#' for comment stripping */
1.181     sjg      2640:                /* Unless previous char was '[', as in modifier :[#] */
                   2641:                if (!(ptr > line && ptr[-1] == '['))
                   2642:                    comment = line_end;
1.127     dsl      2643:            }
                   2644:            ptr++;
1.125     dsl      2645:            if (ch == '\n')
1.127     dsl      2646:                break;
1.290     rillig   2647:            if (!ch_isspace(ch))
1.127     dsl      2648:                /* We are not interested in trailing whitespace */
                   2649:                line_end = ptr;
                   2650:        }
1.125     dsl      2651:
1.127     dsl      2652:        /* Save next 'to be processed' location */
                   2653:        cf->P_ptr = ptr;
                   2654:
                   2655:        /* Check we have a non-comment, non-blank line */
                   2656:        if (line_end == line || comment == line) {
                   2657:            if (ch == 0)
                   2658:                /* At end of file */
                   2659:                return NULL;
                   2660:            /* Parse another line */
1.125     dsl      2661:            continue;
1.127     dsl      2662:        }
1.125     dsl      2663:
1.127     dsl      2664:        /* We now have a line of data */
                   2665:        *line_end = 0;
1.27      christos 2666:
1.127     dsl      2667:        if (flags & PARSE_RAW) {
                   2668:            /* Leave '\' (etc) in line buffer (eg 'for' lines) */
                   2669:            *length = line_end - line;
                   2670:            return line;
                   2671:        }
1.5       cgd      2672:
1.127     dsl      2673:        if (flags & PARSE_SKIP) {
                   2674:            /* Completely ignore non-directives */
                   2675:            if (line[0] != '.')
                   2676:                continue;
                   2677:            /* We could do more of the .else/.elif/.endif checks here */
                   2678:        }
                   2679:        break;
                   2680:     }
1.5       cgd      2681:
1.127     dsl      2682:     /* Brutally ignore anything after a non-escaped '#' in non-commands */
                   2683:     if (comment != NULL && line[0] != '\t') {
                   2684:        line_end = comment;
                   2685:        *line_end = 0;
                   2686:     }
1.5       cgd      2687:
1.127     dsl      2688:     /* If we didn't see a '\\' then the in-situ data is fine */
                   2689:     if (escaped == NULL) {
                   2690:        *length = line_end - line;
                   2691:        return line;
                   2692:     }
1.5       cgd      2693:
1.127     dsl      2694:     /* Remove escapes from '\n' and '#' */
                   2695:     tp = ptr = escaped;
                   2696:     escaped = line;
                   2697:     for (; ; *tp++ = ch) {
                   2698:        ch = *ptr++;
                   2699:        if (ch != '\\') {
                   2700:            if (ch == 0)
                   2701:                break;
                   2702:            continue;
                   2703:        }
1.5       cgd      2704:
1.127     dsl      2705:        ch = *ptr++;
                   2706:        if (ch == 0) {
                   2707:            /* Delete '\\' at end of buffer */
                   2708:            tp--;
                   2709:            break;
                   2710:        }
1.27      christos 2711:
1.130     dsl      2712:        if (ch == '#' && line[0] != '\t')
                   2713:            /* Delete '\\' from before '#' on non-command lines */
1.127     dsl      2714:            continue;
1.27      christos 2715:
1.127     dsl      2716:        if (ch != '\n') {
                   2717:            /* Leave '\\' in buffer for later */
                   2718:            *tp++ = '\\';
                   2719:            /* Make sure we don't delete an escaped ' ' from the line end */
                   2720:            escaped = tp + 1;
                   2721:            continue;
                   2722:        }
1.27      christos 2723:
1.203     joerg    2724:        /* Escaped '\n' replace following whitespace with a single ' ' */
                   2725:        while (ptr[0] == ' ' || ptr[0] == '\t')
                   2726:            ptr++;
                   2727:        ch = ' ';
1.127     dsl      2728:     }
1.27      christos 2729:
1.127     dsl      2730:     /* Delete any trailing spaces - eg from empty continuations */
1.290     rillig   2731:     while (tp > escaped && ch_isspace(tp[-1]))
1.127     dsl      2732:        tp--;
1.27      christos 2733:
1.127     dsl      2734:     *tp = 0;
                   2735:     *length = tp - line;
1.5       cgd      2736:     return line;
                   2737: }
1.1       cgd      2738:
1.284     rillig   2739: /* Read an entire line from the input file. Called only by Parse_File.
1.1       cgd      2740:  *
                   2741:  * Results:
1.284     rillig   2742:  *     A line without its newline.
1.1       cgd      2743:  *
                   2744:  * Side Effects:
                   2745:  *     Only those associated with reading a character
                   2746:  */
                   2747: static char *
1.84      wiz      2748: ParseReadLine(void)
1.1       cgd      2749: {
1.9       jtc      2750:     char         *line;        /* Result */
1.1       cgd      2751:     int                  lineLength;   /* Length of result */
1.95      enami    2752:     int                  lineno;       /* Saved line # */
1.151     dsl      2753:     int                  rval;
1.1       cgd      2754:
1.5       cgd      2755:     for (;;) {
1.127     dsl      2756:        line = ParseGetLine(0, &lineLength);
                   2757:        if (line == NULL)
                   2758:            return NULL;
1.1       cgd      2759:
1.127     dsl      2760:        if (line[0] != '.')
                   2761:            return line;
1.121     dsl      2762:
                   2763:        /*
1.127     dsl      2764:         * The line might be a conditional. Ask the conditional module
                   2765:         * about it and act accordingly
1.121     dsl      2766:         */
1.302     rillig   2767:        switch (Cond_EvalLine(line)) {
1.127     dsl      2768:        case COND_SKIP:
                   2769:            /* Skip to next conditional that evaluates to COND_PARSE.  */
                   2770:            do {
                   2771:                line = ParseGetLine(PARSE_SKIP, &lineLength);
1.302     rillig   2772:            } while (line && Cond_EvalLine(line) != COND_PARSE);
1.127     dsl      2773:            if (line == NULL)
1.121     dsl      2774:                break;
1.127     dsl      2775:            continue;
                   2776:        case COND_PARSE:
                   2777:            continue;
                   2778:        case COND_INVALID:    /* Not a conditional line */
1.151     dsl      2779:            /* Check for .for loops */
                   2780:            rval = For_Eval(line);
                   2781:            if (rval == 0)
                   2782:                /* Not a .for line */
1.1       cgd      2783:                break;
1.151     dsl      2784:            if (rval < 0)
                   2785:                /* Syntax error - error printed, ignore line */
                   2786:                continue;
                   2787:            /* Start of a .for loop */
1.127     dsl      2788:            lineno = curFile->lineno;
1.151     dsl      2789:            /* Accumulate loop lines until matching .endfor */
1.121     dsl      2790:            do {
1.127     dsl      2791:                line = ParseGetLine(PARSE_RAW, &lineLength);
1.121     dsl      2792:                if (line == NULL) {
                   2793:                    Parse_Error(PARSE_FATAL,
1.174     dholland 2794:                             "Unexpected end of file in for loop.");
1.5       cgd      2795:                    break;
1.121     dsl      2796:                }
1.151     dsl      2797:            } while (For_Accum(line));
1.127     dsl      2798:            /* Stash each iteration as a new 'input file' */
                   2799:            For_Run(lineno);
                   2800:            /* Read next line from for-loop buffer */
                   2801:            continue;
1.1       cgd      2802:        }
1.235     rillig   2803:        return line;
1.1       cgd      2804:     }
                   2805: }
                   2806:
1.293     rillig   2807: static int
                   2808: SuffEndTransform(void *target, void *unused MAKE_ATTR_UNUSED)
                   2809: {
                   2810:     Suff_EndTransform(target);
                   2811:     return 0;
                   2812: }
                   2813:
1.1       cgd      2814: /*-
                   2815:  *-----------------------------------------------------------------------
                   2816:  * ParseFinishLine --
                   2817:  *     Handle the end of a dependency group.
                   2818:  *
                   2819:  * Results:
                   2820:  *     Nothing.
                   2821:  *
                   2822:  * Side Effects:
                   2823:  *     inLine set FALSE. 'targets' list destroyed.
                   2824:  *
                   2825:  *-----------------------------------------------------------------------
                   2826:  */
                   2827: static void
1.84      wiz      2828: ParseFinishLine(void)
1.1       cgd      2829: {
                   2830:     if (inLine) {
1.292     rillig   2831:        if (targets != NULL) {
1.293     rillig   2832:            Lst_ForEach(targets, SuffEndTransform, NULL);
1.268     rillig   2833:            Lst_Destroy(targets, ParseHasCommands);
1.263     rillig   2834:        }
1.9       jtc      2835:        targets = NULL;
1.1       cgd      2836:        inLine = FALSE;
                   2837:     }
                   2838: }
1.27      christos 2839:
1.1       cgd      2840:
1.297     rillig   2841: /* Parse a top-level makefile into its component parts, incorporating them
                   2842:  * into the global dependency graph.
1.1       cgd      2843:  *
1.84      wiz      2844:  * Input:
1.297     rillig   2845:  *     name            The name of the file being read
                   2846:  *     fd              The open file to parse; will be closed at the end
1.1       cgd      2847:  */
                   2848: void
1.125     dsl      2849: Parse_File(const char *name, int fd)
1.1       cgd      2850: {
1.117     dsl      2851:     char         *cp;          /* pointer into the line */
                   2852:     char          *line;       /* the line we're working on */
1.170     dholland 2853:     struct loadedfile *lf;
                   2854:
                   2855:     lf = loadfile(name, fd);
1.1       cgd      2856:
                   2857:     inLine = FALSE;
                   2858:     fatals = 0;
1.44      aidan    2859:
1.242     rillig   2860:     if (name == NULL)
                   2861:        name = "(stdin)";
1.170     dholland 2862:
                   2863:     Parse_SetInput(name, 0, -1, loadedfile_nextbuf, lf);
                   2864:     curFile->lf = lf;
1.1       cgd      2865:
                   2866:     do {
1.127     dsl      2867:        for (; (line = ParseReadLine()) != NULL; ) {
1.120     dsl      2868:            if (DEBUG(PARSE))
1.145     christos 2869:                fprintf(debug_file, "ParseReadLine (%d): '%s'\n",
                   2870:                        curFile->lineno, line);
1.1       cgd      2871:            if (*line == '.') {
                   2872:                /*
1.159     dsl      2873:                 * Lines that begin with the special character may be
1.1       cgd      2874:                 * include or undef directives.
1.159     dsl      2875:                 * On the other hand they can be suffix rules (.c.o: ...)
                   2876:                 * or just dependencies for filenames that start '.'.
1.1       cgd      2877:                 */
1.290     rillig   2878:                for (cp = line + 1; ch_isspace(*cp); cp++) {
1.1       cgd      2879:                    continue;
                   2880:                }
1.228     christos 2881:                if (IsInclude(cp, FALSE)) {
1.97      christos 2882:                    ParseDoInclude(cp);
1.117     dsl      2883:                    continue;
                   2884:                }
                   2885:                if (strncmp(cp, "undef", 5) == 0) {
1.1       cgd      2886:                    char *cp2;
1.290     rillig   2887:                    for (cp += 5; ch_isspace(*cp); cp++)
1.1       cgd      2888:                        continue;
1.290     rillig   2889:                    for (cp2 = cp; !ch_isspace(*cp2) && *cp2 != '\0'; cp2++)
1.1       cgd      2890:                        continue;
                   2891:                    *cp2 = '\0';
                   2892:                    Var_Delete(cp, VAR_GLOBAL);
1.117     dsl      2893:                    continue;
1.136     sjg      2894:                } else if (strncmp(cp, "export", 6) == 0) {
1.290     rillig   2895:                    for (cp += 6; ch_isspace(*cp); cp++)
1.136     sjg      2896:                        continue;
1.250     rillig   2897:                    Var_Export(cp, TRUE);
1.136     sjg      2898:                    continue;
1.160     sjg      2899:                } else if (strncmp(cp, "unexport", 8) == 0) {
                   2900:                    Var_UnExport(cp);
                   2901:                    continue;
1.161     sjg      2902:                } else if (strncmp(cp, "info", 4) == 0 ||
                   2903:                           strncmp(cp, "error", 5) == 0 ||
                   2904:                           strncmp(cp, "warning", 7) == 0) {
1.164     sjg      2905:                    if (ParseMessage(cp))
                   2906:                        continue;
1.236     rillig   2907:                }
1.1       cgd      2908:            }
1.27      christos 2909:
1.6       jtc      2910:            if (*line == '\t') {
1.1       cgd      2911:                /*
1.6       jtc      2912:                 * If a line starts with a tab, it can only hope to be
                   2913:                 * a creation command.
1.1       cgd      2914:                 */
1.133     dsl      2915:                cp = line + 1;
1.127     dsl      2916:              shellCommand:
1.290     rillig   2917:                for (; ch_isspace(*cp); cp++) {
1.1       cgd      2918:                    continue;
                   2919:                }
                   2920:                if (*cp) {
1.117     dsl      2921:                    if (!inLine)
1.97      christos 2922:                        Parse_Error(PARSE_FATAL,
1.25      christos 2923:                                     "Unassociated shell command \"%s\"",
1.1       cgd      2924:                                     cp);
1.117     dsl      2925:                    /*
                   2926:                     * So long as it's not a blank line and we're actually
                   2927:                     * in a dependency spec, add the command to the list of
                   2928:                     * commands of all targets in the dependency spec
                   2929:                     */
1.129     christos 2930:                    if (targets) {
1.147     joerg    2931:                        cp = bmake_strdup(cp);
1.268     rillig   2932:                        Lst_ForEach(targets, ParseAddCmd, cp);
1.117     dsl      2933: #ifdef CLEANUP
1.268     rillig   2934:                        Lst_Append(targCmds, cp);
1.117     dsl      2935: #endif
1.129     christos 2936:                    }
1.1       cgd      2937:                }
1.117     dsl      2938:                continue;
                   2939:            }
                   2940:
1.5       cgd      2941: #ifdef SYSVINCLUDE
1.228     christos 2942:            if (IsSysVInclude(line)) {
1.5       cgd      2943:                /*
                   2944:                 * It's an S3/S5-style "include".
                   2945:                 */
1.97      christos 2946:                ParseTraditionalInclude(line);
1.117     dsl      2947:                continue;
                   2948:            }
1.5       cgd      2949: #endif
1.182     christos 2950: #ifdef GMAKEEXPORT
1.290     rillig   2951:            if (strncmp(line, "export", 6) == 0 && ch_isspace(line[6]) &&
1.182     christos 2952:                strchr(line, ':') == NULL) {
                   2953:                /*
1.183     sjg      2954:                 * It's a Gmake "export".
1.182     christos 2955:                 */
                   2956:                ParseGmakeExport(line);
                   2957:                continue;
                   2958:            }
                   2959: #endif
1.117     dsl      2960:            if (Parse_IsVar(line)) {
1.1       cgd      2961:                ParseFinishLine();
1.97      christos 2962:                Parse_DoVar(line, VAR_GLOBAL);
1.117     dsl      2963:                continue;
                   2964:            }
                   2965:
1.127     dsl      2966: #ifndef POSIX
1.117     dsl      2967:            /*
                   2968:             * To make life easier on novices, if the line is indented we
                   2969:             * first make sure the line has a dependency operator in it.
                   2970:             * If it doesn't have an operator and we're in a dependency
                   2971:             * line's script, we assume it's actually a shell command
                   2972:             * and add it to the current list of targets.
                   2973:             */
                   2974:            cp = line;
1.290     rillig   2975:            if (ch_isspace(line[0])) {
                   2976:                while (ch_isspace(*cp))
1.117     dsl      2977:                    cp++;
                   2978:                while (*cp && (ParseIsEscaped(line, cp) ||
1.242     rillig   2979:                        *cp != ':' && *cp != '!')) {
1.117     dsl      2980:                    cp++;
                   2981:                }
1.127     dsl      2982:                if (*cp == '\0') {
                   2983:                    if (inLine) {
                   2984:                        Parse_Error(PARSE_WARNING,
                   2985:                                     "Shell command needs a leading tab");
                   2986:                        goto shellCommand;
                   2987:                    }
                   2988:                }
                   2989:            }
1.11      mycroft  2990: #endif
1.127     dsl      2991:            ParseFinishLine();
1.27      christos 2992:
1.127     dsl      2993:            /*
                   2994:             * For some reason - probably to make the parser impossible -
                   2995:             * a ';' can be used to separate commands from dependencies.
1.158     sjg      2996:             * Attempt to avoid ';' inside substitution patterns.
1.127     dsl      2997:             */
1.158     sjg      2998:            {
                   2999:                int level = 0;
                   3000:
                   3001:                for (cp = line; *cp != 0; cp++) {
                   3002:                    if (*cp == '\\' && cp[1] != 0) {
                   3003:                        cp++;
                   3004:                        continue;
                   3005:                    }
                   3006:                    if (*cp == '$' &&
                   3007:                        (cp[1] == '(' || cp[1] == '{')) {
                   3008:                        level++;
                   3009:                        continue;
                   3010:                    }
                   3011:                    if (level > 0) {
                   3012:                        if (*cp == ')' || *cp == '}') {
                   3013:                            level--;
                   3014:                            continue;
                   3015:                        }
                   3016:                    } else if (*cp == ';') {
                   3017:                        break;
                   3018:                    }
1.117     dsl      3019:                }
                   3020:            }
1.127     dsl      3021:            if (*cp != 0)
                   3022:                /* Terminate the dependency list at the ';' */
1.133     dsl      3023:                *cp++ = 0;
1.127     dsl      3024:            else
                   3025:                cp = NULL;
1.1       cgd      3026:
1.127     dsl      3027:            /*
                   3028:             * We now know it's a dependency line so it needs to have all
                   3029:             * variables expanded before being parsed. Tell the variable
                   3030:             * module to complain if some variable is undefined...
                   3031:             */
1.239     rillig   3032:            line = Var_Subst(line, VAR_CMD, VARE_UNDEFERR|VARE_WANTRES);
1.27      christos 3033:
1.117     dsl      3034:            /*
                   3035:             * Need a non-circular list for the target nodes
                   3036:             */
1.263     rillig   3037:            if (targets != NULL)
1.268     rillig   3038:                Lst_Free(targets);
1.9       jtc      3039:
1.252     rillig   3040:            targets = Lst_Init();
1.117     dsl      3041:            inLine = TRUE;
1.27      christos 3042:
1.117     dsl      3043:            ParseDoDependency(line);
1.127     dsl      3044:            free(line);
                   3045:
                   3046:            /* If there were commands after a ';', add them now */
                   3047:            if (cp != NULL) {
                   3048:                goto shellCommand;
                   3049:            }
1.1       cgd      3050:        }
                   3051:        /*
1.27      christos 3052:         * Reached EOF, but it may be just EOF of an include file...
1.1       cgd      3053:         */
1.123     dsl      3054:     } while (ParseEOF() == CONTINUE);
1.1       cgd      3055:
                   3056:     if (fatals) {
1.163     sjg      3057:        (void)fflush(stdout);
1.63      christos 3058:        (void)fprintf(stderr,
1.175     dholland 3059:            "%s: Fatal errors encountered -- cannot continue",
1.63      christos 3060:            progname);
1.161     sjg      3061:        PrintOnError(NULL, NULL);
1.103     christos 3062:        exit(1);
1.1       cgd      3063:     }
                   3064: }
                   3065:
                   3066: /*-
                   3067:  *---------------------------------------------------------------------
                   3068:  * Parse_Init --
                   3069:  *     initialize the parsing module
                   3070:  *
                   3071:  * Results:
                   3072:  *     none
                   3073:  *
                   3074:  * Side Effects:
                   3075:  *     the parseIncPath list is initialized...
                   3076:  *---------------------------------------------------------------------
                   3077:  */
1.5       cgd      3078: void
1.84      wiz      3079: Parse_Init(void)
1.1       cgd      3080: {
1.152     dsl      3081:     mainNode = NULL;
1.252     rillig   3082:     parseIncPath = Lst_Init();
                   3083:     sysIncPath = Lst_Init();
                   3084:     defIncPath = Lst_Init();
1.276     rillig   3085:     Stack_Init(&includes);
1.45      mycroft  3086: #ifdef CLEANUP
1.252     rillig   3087:     targCmds = Lst_Init();
1.45      mycroft  3088: #endif
1.1       cgd      3089: }
1.9       jtc      3090:
                   3091: void
1.84      wiz      3092: Parse_End(void)
1.9       jtc      3093: {
1.45      mycroft  3094: #ifdef CLEANUP
1.268     rillig   3095:     Lst_Destroy(targCmds, free);
1.9       jtc      3096:     if (targets)
1.268     rillig   3097:        Lst_Free(targets);
                   3098:     Lst_Destroy(defIncPath, Dir_Destroy);
                   3099:     Lst_Destroy(sysIncPath, Dir_Destroy);
                   3100:     Lst_Destroy(parseIncPath, Dir_Destroy);
1.276     rillig   3101:     assert(Stack_IsEmpty(&includes));
                   3102:     Stack_Done(&includes);
1.45      mycroft  3103: #endif
1.9       jtc      3104: }
1.27      christos 3105:
1.1       cgd      3106:
                   3107: /*-
                   3108:  *-----------------------------------------------------------------------
                   3109:  * Parse_MainName --
                   3110:  *     Return a Lst of the main target to create for main()'s sake. If
                   3111:  *     no such target exists, we Punt with an obnoxious error message.
                   3112:  *
                   3113:  * Results:
                   3114:  *     A Lst of the single node to create.
                   3115:  *
                   3116:  * Side Effects:
                   3117:  *     None.
                   3118:  *
                   3119:  *-----------------------------------------------------------------------
                   3120:  */
                   3121: Lst
1.84      wiz      3122: Parse_MainName(void)
1.1       cgd      3123: {
1.37      fair     3124:     Lst           mainList;    /* result list */
1.1       cgd      3125:
1.252     rillig   3126:     mainList = Lst_Init();
1.1       cgd      3127:
1.152     dsl      3128:     if (mainNode == NULL) {
1.97      christos 3129:        Punt("no target to make.");
1.246     rillig   3130:        /*NOTREACHED*/
1.1       cgd      3131:     } else if (mainNode->type & OP_DOUBLEDEP) {
1.268     rillig   3132:        Lst_Append(mainList, mainNode);
                   3133:        Lst_AppendAll(mainList, mainNode->cohorts);
1.1       cgd      3134:     }
1.5       cgd      3135:     else
1.268     rillig   3136:        Lst_Append(mainList, mainNode);
1.81      pk       3137:     Var_Append(".TARGETS", mainNode->name, VAR_GLOBAL);
1.235     rillig   3138:     return mainList;
1.59      christos 3139: }

CVSweb <webmaster@jp.NetBSD.org>