diff options
author | Ron Yorston <rmy@pobox.com> | 2024-05-28 12:22:54 +0100 |
---|---|---|
committer | Ron Yorston <rmy@pobox.com> | 2024-05-28 12:22:54 +0100 |
commit | 11b3ae755cd67c298bc0a93b1a9872d1eecdbb00 (patch) | |
tree | 1dd1f18b12cf02ecbb4d46f37212e472667a9019 | |
parent | 208d9858409f823d533d1e95396dde00be03d7d3 (diff) | |
download | busybox-w32-11b3ae755cd67c298bc0a93b1a9872d1eecdbb00.tar.gz busybox-w32-11b3ae755cd67c298bc0a93b1a9872d1eecdbb00.tar.bz2 busybox-w32-11b3ae755cd67c298bc0a93b1a9872d1eecdbb00.zip |
make: fixes to -q option
The -q option returns an exit status to indicate if targets are
up-to-date (0) or in need of updating (1) but without updating
them. As an exception (imported from GNU make) build commands
with a '+' prefix are executed.
pdpmake didn't implement the exception. Doing so required moving
handling of the -q option down into docmds().
Saves 48 bytes.
-rw-r--r-- | miscutils/make.c | 72 | ||||
-rwxr-xr-x | testsuite/make.tests | 7 |
2 files changed, 43 insertions, 36 deletions
diff --git a/miscutils/make.c b/miscutils/make.c index 70fd30440..a4fecd640 100644 --- a/miscutils/make.c +++ b/miscutils/make.c | |||
@@ -2363,6 +2363,12 @@ docmds(struct name *np, struct cmd *cp) | |||
2363 | fflush_all(); | 2363 | fflush_all(); |
2364 | } | 2364 | } |
2365 | 2365 | ||
2366 | if (quest && sdomake != TRUE + 1) { | ||
2367 | // MAKE_FAILURE means rebuild is needed | ||
2368 | estat |= MAKE_FAILURE | MAKE_DIDSOMETHING; | ||
2369 | continue; | ||
2370 | } | ||
2371 | |||
2366 | if (sdomake) { | 2372 | if (sdomake) { |
2367 | // Get the shell to execute it | 2373 | // Get the shell to execute it |
2368 | int status; | 2374 | int status; |
@@ -2378,16 +2384,11 @@ docmds(struct name *np, struct cmd *cp) | |||
2378 | } else if (status != 0 && !signore) { | 2384 | } else if (status != 0 && !signore) { |
2379 | if (!posix && WIFSIGNALED(status)) | 2385 | if (!posix && WIFSIGNALED(status)) |
2380 | remove_target(); | 2386 | remove_target(); |
2381 | if (errcont) { | 2387 | if (doinclude) { |
2382 | diagnostic("failed to build '%s'", np->n_name); | ||
2383 | estat |= MAKE_FAILURE; | ||
2384 | free(command); | ||
2385 | break; | ||
2386 | } else if (doinclude) { | ||
2387 | warning("failed to build '%s'", np->n_name); | 2388 | warning("failed to build '%s'", np->n_name); |
2388 | } else { | 2389 | } else { |
2389 | const char *err_type = NULL; | 2390 | const char *err_type = NULL; |
2390 | int err_value; | 2391 | int err_value = 1; |
2391 | 2392 | ||
2392 | if (WIFEXITED(status)) { | 2393 | if (WIFEXITED(status)) { |
2393 | err_type = "exit"; | 2394 | err_type = "exit"; |
@@ -2397,11 +2398,20 @@ docmds(struct name *np, struct cmd *cp) | |||
2397 | err_value = WTERMSIG(status); | 2398 | err_value = WTERMSIG(status); |
2398 | } | 2399 | } |
2399 | 2400 | ||
2400 | if (err_type) | 2401 | if (!quest || err_value == 127) { |
2401 | error("failed to build '%s' %s %d", np->n_name, | 2402 | if (err_type) |
2402 | err_type, err_value); | 2403 | diagnostic("failed to build '%s' %s %d", |
2403 | else | 2404 | np->n_name, err_type, err_value); |
2404 | error("failed to build '%s'", np->n_name); | 2405 | else |
2406 | diagnostic("failed to build '%s'", np->n_name); | ||
2407 | } | ||
2408 | |||
2409 | if (errcont) { | ||
2410 | estat |= MAKE_FAILURE; | ||
2411 | free(command); | ||
2412 | break; | ||
2413 | } | ||
2414 | exit(2); | ||
2405 | } | 2415 | } |
2406 | } | 2416 | } |
2407 | } | 2417 | } |
@@ -2558,7 +2568,7 @@ make(struct name *np, int level) | |||
2558 | } | 2568 | } |
2559 | 2569 | ||
2560 | // Reset flag to detect duplicate prerequisites | 2570 | // Reset flag to detect duplicate prerequisites |
2561 | if (!quest && !(np->n_flag & N_DOUBLE)) { | 2571 | if (!(np->n_flag & N_DOUBLE)) { |
2562 | for (rp = np->n_rule; rp; rp = rp->r_next) { | 2572 | for (rp = np->n_rule; rp; rp = rp->r_next) { |
2563 | for (dp = rp->r_dep; dp; dp = dp->d_next) { | 2573 | for (dp = rp->r_dep; dp; dp = dp->d_next) { |
2564 | dp->d_name->n_flag &= ~N_MARK; | 2574 | dp->d_name->n_flag &= ~N_MARK; |
@@ -2582,10 +2592,8 @@ make(struct name *np, int level) | |||
2582 | if (!rp->r_dep) | 2592 | if (!rp->r_dep) |
2583 | dtim = np->n_tim; | 2593 | dtim = np->n_tim; |
2584 | // Reset flag to detect duplicate prerequisites | 2594 | // Reset flag to detect duplicate prerequisites |
2585 | if (!quest) { | 2595 | for (dp = rp->r_dep; dp; dp = dp->d_next) { |
2586 | for (dp = rp->r_dep; dp; dp = dp->d_next) { | 2596 | dp->d_name->n_flag &= ~N_MARK; |
2587 | dp->d_name->n_flag &= ~N_MARK; | ||
2588 | } | ||
2589 | } | 2597 | } |
2590 | } | 2598 | } |
2591 | for (dp = rp->r_dep; dp; dp = dp->d_next) { | 2599 | for (dp = rp->r_dep; dp; dp = dp->d_next) { |
@@ -2594,22 +2602,19 @@ make(struct name *np, int level) | |||
2594 | 2602 | ||
2595 | // Make strings of out-of-date prerequisites (for $?), | 2603 | // Make strings of out-of-date prerequisites (for $?), |
2596 | // all prerequisites (for $+) and deduplicated prerequisites | 2604 | // all prerequisites (for $+) and deduplicated prerequisites |
2597 | // (for $^). But not if we were invoked with -q. | 2605 | // (for $^). |
2598 | if (!quest) { | 2606 | if (timespec_le(&np->n_tim, &dp->d_name->n_tim)) { |
2599 | if (timespec_le(&np->n_tim, &dp->d_name->n_tim)) { | 2607 | if (posix || !(dp->d_name->n_flag & N_MARK)) |
2600 | if (posix || !(dp->d_name->n_flag & N_MARK)) | 2608 | oodate = xappendword(oodate, dp->d_name->n_name); |
2601 | oodate = xappendword(oodate, dp->d_name->n_name); | ||
2602 | } | ||
2603 | allsrc = xappendword(allsrc, dp->d_name->n_name); | ||
2604 | if (!(dp->d_name->n_flag & N_MARK)) | ||
2605 | dedup = xappendword(dedup, dp->d_name->n_name); | ||
2606 | dp->d_name->n_flag |= N_MARK; | ||
2607 | } | 2609 | } |
2610 | allsrc = xappendword(allsrc, dp->d_name->n_name); | ||
2611 | if (!(dp->d_name->n_flag & N_MARK)) | ||
2612 | dedup = xappendword(dedup, dp->d_name->n_name); | ||
2613 | dp->d_name->n_flag |= N_MARK; | ||
2608 | dtim = *timespec_max(&dtim, &dp->d_name->n_tim); | 2614 | dtim = *timespec_max(&dtim, &dp->d_name->n_tim); |
2609 | } | 2615 | } |
2610 | if ((np->n_flag & N_DOUBLE)) { | 2616 | if ((np->n_flag & N_DOUBLE)) { |
2611 | if (!quest && ((np->n_flag & N_PHONY) || | 2617 | if (((np->n_flag & N_PHONY) || timespec_le(&np->n_tim, &dtim))) { |
2612 | timespec_le(&np->n_tim, &dtim))) { | ||
2613 | if (!(estat & MAKE_FAILURE)) { | 2618 | if (!(estat & MAKE_FAILURE)) { |
2614 | estat |= make1(np, rp->r_cmd, oodate, allsrc, | 2619 | estat |= make1(np, rp->r_cmd, oodate, allsrc, |
2615 | dedup, locdep); | 2620 | dedup, locdep); |
@@ -2633,19 +2638,14 @@ make(struct name *np, int level) | |||
2633 | np->n_flag |= N_DONE; | 2638 | np->n_flag |= N_DONE; |
2634 | np->n_flag &= ~N_DOING; | 2639 | np->n_flag &= ~N_DOING; |
2635 | 2640 | ||
2636 | if (quest) { | 2641 | if (!(np->n_flag & N_DOUBLE) && |
2637 | if (timespec_le(&np->n_tim, &dtim)) { | ||
2638 | // MAKE_FAILURE means rebuild is needed | ||
2639 | estat = MAKE_FAILURE | MAKE_DIDSOMETHING; | ||
2640 | } | ||
2641 | } else if (!(np->n_flag & N_DOUBLE) && | ||
2642 | ((np->n_flag & N_PHONY) || (timespec_le(&np->n_tim, &dtim)))) { | 2642 | ((np->n_flag & N_PHONY) || (timespec_le(&np->n_tim, &dtim)))) { |
2643 | if (!(estat & MAKE_FAILURE)) { | 2643 | if (!(estat & MAKE_FAILURE)) { |
2644 | if (sc_cmd) | 2644 | if (sc_cmd) |
2645 | estat |= make1(np, sc_cmd, oodate, allsrc, dedup, impdep); | 2645 | estat |= make1(np, sc_cmd, oodate, allsrc, dedup, impdep); |
2646 | else if (!doinclude && level == 0 && !(estat & MAKE_DIDSOMETHING)) | 2646 | else if (!doinclude && level == 0 && !(estat & MAKE_DIDSOMETHING)) |
2647 | warning("nothing to be done for %s", np->n_name); | 2647 | warning("nothing to be done for %s", np->n_name); |
2648 | } else if (!doinclude) { | 2648 | } else if (!doinclude && !quest) { |
2649 | diagnostic("'%s' not built due to errors", np->n_name); | 2649 | diagnostic("'%s' not built due to errors", np->n_name); |
2650 | } | 2650 | } |
2651 | free(oodate); | 2651 | free(oodate); |
diff --git a/testsuite/make.tests b/testsuite/make.tests index c2b62532a..e4d635141 100755 --- a/testsuite/make.tests +++ b/testsuite/make.tests | |||
@@ -116,6 +116,13 @@ bar: | |||
116 | baz: | 116 | baz: |
117 | @: | 117 | @: |
118 | ' | 118 | ' |
119 | # Build commands with a '+' prefix are executed even with the -q option. | ||
120 | testing "make execute build command with + prefix and -q" \ | ||
121 | "make -q -f - 2>/dev/null" "OK\n" "" ' | ||
122 | all: bar | ||
123 | bar: | ||
124 | @+echo OK | ||
125 | ' | ||
119 | 126 | ||
120 | # The -t option touches files that are out-of-date unless the target | 127 | # The -t option touches files that are out-of-date unless the target |
121 | # has no commands or they're already up-to-date. | 128 | # has no commands or they're already up-to-date. |