⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 make1.c

📁 Boost provides free peer-reviewed portable C++ source libraries. We emphasize libraries that work
💻 C
📖 第 1 页 / 共 3 页
字号:
    void *closure, int status, timing_info* time, char *executed_command,    char *command_output){    TARGET* built = (TARGET*)closure;    call_timing_rule(built, time);    if (DEBUG_EXECCMD)        printf("%f sec system; %f sec user\n", time->system, time->user);    call_action_rule(built, status, time, executed_command, command_output);        push_state(&state_stack, built, NULL, T_STATE_MAKE1D)->status = status;}/* * make1d() - handle command execution completion and call back make1c() */static voidmake1d(state *pState){	TARGET	*t = pState->t;	CMD	*cmd = (CMD *)t->cmds;	int status = pState->status;	/* Execcmd() has completed.  All we need to do is fiddle with the */	/* status and signal our completion so make1c() can run the next */	/* command.  On interrupts, we bail heavily. */        if ( t->flags & T_FLAG_FAIL_EXPECTED )        {          /* invert execution result when FAIL_EXPECTED was applied */          switch (status)          {            case EXEC_CMD_FAIL: status = EXEC_CMD_OK; break;            case EXEC_CMD_OK:   status = EXEC_CMD_FAIL; break;            default:              ;          }        }        	if( status == EXEC_CMD_FAIL && ( cmd->rule->actions->flags & RULE_IGNORE ) )	    status = EXEC_CMD_OK;	/* On interrupt, set intr so _everything_ fails */	if( status == EXEC_CMD_INTR )	    ++intr;	if( status == EXEC_CMD_FAIL && DEBUG_MAKE )	{	    /* Print command text on failure */	    if( !DEBUG_EXEC )		printf( "%s\n", cmd->buf );	    printf( "...failed %s ", cmd->rule->name );	    list_print( lol_get( &cmd->args, 0 ) );	    printf( "...\n" );	}	if (status == EXEC_CMD_FAIL)		if( globs.quitquick ) ++intr;	/* If the command was interrupted or failed and the target */	/* is not "precious", remove the targets */	if( status != EXEC_CMD_OK && !( cmd->rule->actions->flags & RULE_TOGETHER ) )	{	    LIST *targets = lol_get( &cmd->args, 0 );	    for( ; targets; targets = list_next( targets ) )		if( !unlink( targets->string ) )		    printf( "...removing %s\n", targets->string );	}	/* Free this command and call make1c() to move onto next command. */	t->status = status;	t->cmds = (char *)cmd_next( cmd );	cmd_free( cmd );	pState->curstate = T_STATE_MAKE1C;}/* * swap_settings() - replace the settings from the current module and *                   target with those from the new module and target */static void swap_settings(    module_t** current_module    , TARGET** current_target    , module_t* new_module    , TARGET* new_target){    if (new_module == root_module())        new_module = 0;        if (new_target == *current_target && new_module == *current_module)        return;    if (*current_target)        popsettings( (*current_target)->settings );            if (new_module != *current_module)    {        if (*current_module)            exit_module( *current_module );        *current_module = new_module;                if (new_module)            enter_module( new_module );    }    *current_target = new_target;    if (new_target)        pushsettings( new_target->settings );}/* * make1cmds() - turn ACTIONS into CMDs, grouping, splitting, etc * * Essentially copies a chain of ACTIONs to a chain of CMDs,  * grouping RULE_TOGETHER actions, splitting RULE_PIECEMEAL actions, * and handling RULE_NEWSRCS actions.  The result is a chain of * CMDs which can be expanded by var_string() and executed with * execcmd(). */static CMD *make1cmds( TARGET *t ){	CMD *cmds = 0;	LIST *shell = 0;                module_t *settings_module = 0;        TARGET *settings_target = 0;        	/* Step through actions */	/* Actions may be shared with other targets or grouped with */	/* RULE_TOGETHER, so actions already seen are skipped. */                ACTIONS* a0;	for(a0 = t->actions ; a0; a0 = a0->next )	{	    RULE    *rule = a0->action->rule;            rule_actions *actions = rule->actions;	    SETTINGS *boundvars;	    LIST    *nt, *ns;	    ACTIONS *a1;	    int	    start, chunk, length;	    /* Only do rules with commands to execute. */	    /* If this action has already been executed, use saved status */	    if( !actions || a0->action->running )		continue;	    a0->action->running = 1;	    	    /* Make LISTS of targets and sources */	    /* If `execute together` has been specified for this rule, tack */	    /* on sources from each instance of this rule for this target. */	    nt = make1list( L0, a0->action->targets, 0 );	    ns = make1list( L0, a0->action->sources, actions->flags );	    if( actions->flags & RULE_TOGETHER )		for( a1 = a0->next; a1; a1 = a1->next )		    if( a1->action->rule == rule && !a1->action->running )	    {		ns = make1list( ns, a1->action->sources, actions->flags );		a1->action->running = 1;	    }	    /* If doing only updated (or existing) sources, but none have */	    /* been updated (or exist), skip this action. */	    if( !ns && ( actions->flags & ( RULE_NEWSRCS | RULE_EXISTING ) ) )	    {		list_free( nt );		continue;	    }            swap_settings( &settings_module, &settings_target, rule->module, t );            if (!shell)                shell = var_get( "JAMSHELL" );	/* shell is per-target */                	    /* If we had 'actions xxx bind vars' we bind the vars now */	    boundvars = make1settings( actions->bindlist );	    pushsettings( boundvars );	    /*	     * Build command, starting with all source args. 	     *	     * If cmd_new returns 0, it's because the resulting command	     * length is > MAXLINE.  In this case, we'll slowly reduce	     * the number of source arguments presented until it does	     * fit.  This only applies to actions that allow PIECEMEAL 	     * commands.	     *	     * While reducing slowly takes a bit of compute time to get	     * things just right, it's worth it to get as close to MAXLINE	     * as possible, because launching the commands we're executing 	     * is likely to be much more compute intensive!	     *	     * Note we loop through at least once, for sourceless actions.	     */	    start = 0;	    chunk = length = list_length( ns );	    do	    {		/* Build cmd: cmd_new consumes its lists. */		CMD *cmd = cmd_new( rule, 			list_copy( L0, nt ), 			list_sublist( ns, start, chunk ),			list_copy( L0, shell ) );		if( cmd )		{		    /* It fit: chain it up. */		    if( !cmds ) cmds = cmd;		    else cmds->tail->next = cmd;		    cmds->tail = cmd;		    start += chunk;		}		else if( ( actions->flags & RULE_PIECEMEAL ) && chunk > 1 )		{		    /* Reduce chunk size slowly. */		    chunk = chunk * 9 / 10;		}		else		{		    /* Too long and not splittable. */		    printf( "%s actions too long (max %d):\n", 			rule->name, MAXLINE );                    /* Tell the user what didn't fit */                    cmd = cmd_new(                        rule, list_copy( L0, nt ), 			list_sublist( ns, start, chunk ),			list_new( L0, newstr( "%" ) ) );                    printf( cmd->buf );                		    exit( EXITBAD );		}	    }	    while( start < length );	    /* These were always copied when used. */	    list_free( nt );	    list_free( ns );	    /* Free the variables whose values were bound by */	    /* 'actions xxx bind vars' */	    popsettings( boundvars );	    freesettings( boundvars );	}        swap_settings( &settings_module, &settings_target, 0, 0 );	return cmds;}/* * make1list() - turn a list of targets into a LIST, for $(<) and $(>) */static LIST *make1list( 	LIST	*l,	TARGETS	*targets,	int	flags ){    for( ; targets; targets = targets->next )    {	TARGET *t = targets->target;	if( t->binding == T_BIND_UNBOUND )	    make1bind( t );    if ( ( flags & RULE_EXISTING ) && ( flags & RULE_NEWSRCS ) )    {        if ( t->binding != T_BIND_EXISTS && t->fate <= T_FATE_STABLE)            continue;    }    else    {         if( ( flags & RULE_EXISTING ) && t->binding != T_BIND_EXISTS )            continue;        if( ( flags & RULE_NEWSRCS ) && t->fate <= T_FATE_STABLE )            continue;    }	/* Prohibit duplicates for RULE_TOGETHER */	if( flags & RULE_TOGETHER )	{	    LIST *m;	    for( m = l; m; m = m->next )		if( !strcmp( m->string, t->boundname ) )		    break;	    if( m )		continue;	}	/* Build new list */	l = list_new( l, copystr( t->boundname ) );    }    return l;}/* * make1settings() - for vars that get bound values, build up replacement lists */static SETTINGS *make1settings( LIST *vars ){	SETTINGS *settings = 0;	for( ; vars; vars = list_next( vars ) )	{	    LIST *l = var_get( vars->string );	    LIST *nl = 0;	    for( ; l; l = list_next( l ) ) 	    {		TARGET *t = bindtarget( l->string );		/* Make sure the target is bound */		if( t->binding == T_BIND_UNBOUND )		    make1bind( t );		/* Build new list */		nl = list_new( nl, copystr( t->boundname ) );	    }	    /* Add to settings chain */	    settings = addsettings( settings, VAR_SET, vars->string, nl );	}	return settings;}/* * make1bind() - bind targets that weren't bound in dependency analysis * * Spot the kludge!  If a target is not in the dependency tree, it didn't  * get bound by make0(), so we have to do it here.  Ugly. */static voidmake1bind( 	TARGET	*t ){	if( t->flags & T_FLAG_NOTFILE )	    return;	pushsettings( t->settings );	t->boundname = search( t->name, &t->time, 0 );	t->binding = t->time ? T_BIND_EXISTS : T_BIND_MISSING;	popsettings( t->settings );}

⌨️ 快捷键说明

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