main.c

来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 647 行 · 第 1/2 页

C
647
字号
        }
        if( strpbrk( p, "=#" ) != NULL ) {     /* is macro=defn */
            handleMacroDefn( p );
        } else {                /* is a target */
            handleTarg( p );
        }
    } // while( *++argv != NULL )

    if( Glob.microsoft && Glob.unix ) {
        PrtMsg( ERR | INCOMPATIBLE__OPTIONS, select, option );
        Usage();
    }

    Glob.macreadonly = FALSE;

    {
        // 120 allows for 30 options.
        size_t const    optsize = 120 + (*log_name ? strlen( *log_name ) + 1: 0) + 1;
        char * const    makeopts = MallocSafe( optsize );
        unsigned        opt_index;
        char            default_option[] = " -?";

        makeopts[0] = 0;
        opt_index = 'a' - 1;
        while( ++opt_index <= 'z' ) {
            if( options[opt_index + 1] ) {
                switch( opt_index ) {
                case 'f':
                case 'n':
                    break;
                case 'l':
                    strcat( makeopts, *makeopts ? " -l " : "-l " );
                    strcat( makeopts, *log_name );
                    break;
                case 'm':
                    if( Glob.nomakeinit ) {
                        strcat( makeopts, *makeopts ? " -m" : "-m" );
                    }
                    if( Glob.microsoft ) {
                        strcat( makeopts, *makeopts ? " -ms" : "-ms" );
                    }
                    break;
                case 's':
                    if( Glob.silentno ) {
                        strcat( makeopts, *makeopts ? " -sn" : "-sn" );
                    } else {
                        strcat( makeopts, *makeopts ? " -s" : "-s" );
                    }
                    break;
                default:
                    default_option[2] = (char)opt_index;
                    strcat( makeopts, default_option + (int)(*makeopts == '\0') );
                }
            }

        }
        return( makeopts );
    }
}


STATIC const char *procLogName( const char * const *argv )
/*********************************************************
 Find log file name
 */
{
    const char *p;      /* working pointer to *argv                 */

    while( *++argv != NULL ) {
        p = *argv;
        if( ((p[0] == '-') || (p[0] == Glob.swchar)) &&
                (tolower( p[1] ) == 'l') && (p[2] == NULLCHAR) ) {
            return( ((p = *++argv) == NULL || (p[0] == '-')
                || (p[0] == Glob.swchar)) ? NULL : p );
        }
    }
    return( NULL );
}

STATIC void parseFiles( void )
/*****************************
 * Parse()s each of the files in filesToDo
 * post:    filesToDo == NULL
 */
{
    char    *p;
    NODE    *cur;
    NODE    *newhead;
    RET_T   ret;

    Glob.preproc = TRUE;            /* turn on preprocessor */

                                    /* process makeinit */
    if( !Glob.nomakeinit ) {
        if( Glob.microsoft ) {
            ret = InsFile( TOOLSINI_NAME, TRUE );
        } else {
            ret = InsFile( MAKEINIT_NAME, TRUE );
        }
        if( ret == RET_SUCCESS ) {
            setFirstTarget( Parse() );
            if( firstTargFound != NULL ) {
                PrtMsg( WRN | MAKEINIT_HAS_TARGET );
            }
        }
    }

    if( filesToDo == NULL ) {
        ret = InsFile( MAKEFILE_NAME, FALSE );
        if( ret == RET_SUCCESS ) {
            setFirstTarget( Parse() );
#ifdef MAKEFILE_ALT
        } else if( (ret = InsFile( MAKEFILE_ALT, FALSE )) == RET_SUCCESS ) {
            setFirstTarget( Parse() );
#endif
        }
    } else {
        newhead = NULL;     /* reverse order of files stacked by procFlags */
        while( filesToDo != NULL ) {
            cur = filesToDo;
            filesToDo = cur->next;

            cur->next = newhead;
            newhead = cur;
        }

        while( newhead != NULL ) {
            cur = newhead;
            newhead = cur->next;
            p = cur->name;
            FreeSafe( cur );
            if( p[0] == '-' && p[1] == NULLCHAR ) { /* handle -f - */
                InsOpenFile( STDIN );
                ret = RET_SUCCESS;
            } else {
                ret = InsFile( p, FALSE );
            }
            if( ret == RET_SUCCESS ) {
                setFirstTarget( Parse() );
            } else {
                PrtMsg( ERR | UNABLE_TO_INCLUDE, p );
            }
        }
    }

    if( !Glob.nomakeinit ) {
        if( !Glob.microsoft ) {
            ret = InsFile( MAKEFINI_NAME, TRUE );
            if( ret == RET_SUCCESS ) {
                setFirstTarget( Parse() );
            }
        }
    }

    Glob.preproc = FALSE;           /* turn off preprocessor */
}


STATIC void print( void )
/***********************/
{
    PrintMacros();
    PrintSuffixes();
    PrintTargets();
}

STATIC void ignoreNoCommands( const TLIST *targ )
{
    TLIST const     *current;

    current = targ;
    // set targets to be OK if there are no commands to update it
    while( current != NULL ) {
        current->target->allow_nocmd = TRUE;
        current = current->next;
    }
}

STATIC RET_T doMusts( void )
/**************************/
{
    RET_T   ret;

    if( firstTargFound == NULL && mustTargs == NULL ) {
        PrtMsg( FTL | NO_TARGETS_SPECIFIED );
    }

    UpdateInit();

    if( mustTargs == NULL ) {
        ignoreNoCommands( firstTargFound );
        ret = MakeList( firstTargFound );
    } else {
        ignoreNoCommands( mustTargs );
        ret = MakeList( mustTargs );
    }

    UpdateFini();
    return( ret );
}


STATIC void globInit( void )
/**************************/
{
    Glob.swchar = (char)SwitchChar();
}


STATIC void init( char const * const *argv )
/******************************************/
{
    char        *makeopts;
    char const  *log_name;

    LogInit( NULL );
    globInit();
    MemInit();          /* memory handlers          */
    if( !MsgInit() ) {
        exit( EXIT_FAILURE );
    }
    VecInit();          /* vector strings           */
    CacheInit();        /* directory cacheing       */
    MacroInit();        /* initialize macros        */
    TargetInit();       /* target must come before  */
    SuffixInit();       /* suffix                   */
    LexInit();
    ExecInit();
    AutoDepInit();

#ifdef __NT__
#if __WATCOMC__ >= 1100
    _fileinfo = 0;      /* C Library Kludge -------------------------- */
#endif
#endif
#ifdef __OS2__
    _grow_handles( 100 ); /* Some OS/2 versions allow only 20 files open by default */
#endif
    filesToDo = NULL;
    mustTargs = NULL;
    log_name = NULL;
    LogFini();
    LogInit( procLogName( argv ) );
    makeopts = procFlags( argv, &log_name );
    ParseInit();
    doBuiltIns( makeopts );
    FreeSafe( makeopts );
}


int ExitSafe( int rc )
/********************/
{
    static BOOLEAN  busy = FALSE;   /* recursion protection */

    if( !busy ) {
        busy = TRUE;
        if( rc == EXIT_ERROR || rc == EXIT_FATAL ) {
            PrtMsg( ERR | MAKE_ABORT );
        }
#ifndef NDEBUG
        while( filesToDo != NULL ) {
            NODE * const cur = filesToDo;
            filesToDo = cur->next;
            FreeSafe( cur );
        }
        if( mustTargs != NULL ) {
            FreeTList( mustTargs );
        }
        if( firstTargFound != NULL ) {
            FreeTList( firstTargFound );
        }
#endif

        AutoDepFini();
        ExecFini();
        LexFini();
        SuffixFini();       /* suffix must come before target   */
        TargetFini();
        MacroFini();
        CacheFini();
        VecFini();
#ifndef NDEBUG
        PutEnvFini();
        DLLFini();
#endif
        MemFini();
        MsgFini();
        LogFini();
    }

    return( rc );
}

#ifndef __WATCOMC__
char **_argv;
#endif
int main( int argc, char * const *argv )
/*********************************************/
{
    assert( argv[argc] == NULL );       /* part of ANSI standard */
#ifndef __WATCOMC__
    _argv = (char**)argv;
#endif
    InitSignals();
    InitHardErr();
    init( (const char **)argv );        /* initialize, process cmdline */
    Header();
    parseFiles();
    if( Glob.print ) {
        print();
        return( ExitSafe( EXIT_OK ) );
    }
    if( Glob.erroryet ) {
        return( ExitSafe( EXIT_ERROR ) );
    }
    if( doMusts() != RET_SUCCESS ) {
        return( ExitSafe( EXIT_ERROR ) );
    }
    ParseFini();
    return( ExitSafe( EXIT_OK ) );
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?