diff options
| author | Denys Vlasenko <vda.linux@googlemail.com> | 2011-02-02 19:05:25 +0100 |
|---|---|---|
| committer | Denys Vlasenko <vda.linux@googlemail.com> | 2011-02-02 19:05:25 +0100 |
| commit | 6307357effb79c8fbc6ccc9d4528c8c1c48a4831 (patch) | |
| tree | 332d6bc33b792407e2d569c6563887b615ef0392 /libbb | |
| parent | b72baeb00328576df415f9a4b4f3d5f202e3be11 (diff) | |
| download | busybox-w32-6307357effb79c8fbc6ccc9d4528c8c1c48a4831.tar.gz busybox-w32-6307357effb79c8fbc6ccc9d4528c8c1c48a4831.tar.bz2 busybox-w32-6307357effb79c8fbc6ccc9d4528c8c1c48a4831.zip | |
move nofork_save_area from libbb.h to vfork_daemon_rexec.c
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'libbb')
| -rw-r--r-- | libbb/getopt32.c | 2 | ||||
| -rw-r--r-- | libbb/vfork_daemon_rexec.c | 48 |
2 files changed, 20 insertions, 30 deletions
diff --git a/libbb/getopt32.c b/libbb/getopt32.c index 25bae319e..abd412043 100644 --- a/libbb/getopt32.c +++ b/libbb/getopt32.c | |||
| @@ -531,7 +531,7 @@ getopt32(char **argv, const char *applet_opts, ...) | |||
| 531 | 531 | ||
| 532 | /* In case getopt32 was already called: | 532 | /* In case getopt32 was already called: |
| 533 | * reset the libc getopt() function, which keeps internal state. | 533 | * reset the libc getopt() function, which keeps internal state. |
| 534 | * run_nofork_applet_prime() does this, but we might end up here | 534 | * run_nofork_applet() does this, but we might end up here |
| 535 | * also via gunzip_main() -> gzip_main(). Play safe. | 535 | * also via gunzip_main() -> gzip_main(). Play safe. |
| 536 | */ | 536 | */ |
| 537 | #ifdef __GLIBC__ | 537 | #ifdef __GLIBC__ |
diff --git a/libbb/vfork_daemon_rexec.c b/libbb/vfork_daemon_rexec.c index cb4781a59..af938bed3 100644 --- a/libbb/vfork_daemon_rexec.c +++ b/libbb/vfork_daemon_rexec.c | |||
| @@ -68,17 +68,22 @@ pid_t FAST_FUNC xspawn(char **argv) | |||
| 68 | } | 68 | } |
| 69 | 69 | ||
| 70 | #if ENABLE_FEATURE_PREFER_APPLETS | 70 | #if ENABLE_FEATURE_PREFER_APPLETS |
| 71 | void FAST_FUNC save_nofork_data(struct nofork_save_area *save) | 71 | struct nofork_save_area { |
| 72 | jmp_buf die_jmp; | ||
| 73 | const char *applet_name; | ||
| 74 | uint32_t option_mask32; | ||
| 75 | int die_sleep; | ||
| 76 | uint8_t xfunc_error_retval; | ||
| 77 | }; | ||
| 78 | static void save_nofork_data(struct nofork_save_area *save) | ||
| 72 | { | 79 | { |
| 73 | memcpy(&save->die_jmp, &die_jmp, sizeof(die_jmp)); | 80 | memcpy(&save->die_jmp, &die_jmp, sizeof(die_jmp)); |
| 74 | save->applet_name = applet_name; | 81 | save->applet_name = applet_name; |
| 75 | save->xfunc_error_retval = xfunc_error_retval; | 82 | save->xfunc_error_retval = xfunc_error_retval; |
| 76 | save->option_mask32 = option_mask32; | 83 | save->option_mask32 = option_mask32; |
| 77 | save->die_sleep = die_sleep; | 84 | save->die_sleep = die_sleep; |
| 78 | save->saved = 1; | ||
| 79 | } | 85 | } |
| 80 | 86 | static void restore_nofork_data(struct nofork_save_area *save) | |
| 81 | void FAST_FUNC restore_nofork_data(struct nofork_save_area *save) | ||
| 82 | { | 87 | { |
| 83 | memcpy(&die_jmp, &save->die_jmp, sizeof(die_jmp)); | 88 | memcpy(&die_jmp, &save->die_jmp, sizeof(die_jmp)); |
| 84 | applet_name = save->applet_name; | 89 | applet_name = save->applet_name; |
| @@ -87,19 +92,17 @@ void FAST_FUNC restore_nofork_data(struct nofork_save_area *save) | |||
| 87 | die_sleep = save->die_sleep; | 92 | die_sleep = save->die_sleep; |
| 88 | } | 93 | } |
| 89 | 94 | ||
| 90 | int FAST_FUNC run_nofork_applet_prime(struct nofork_save_area *old, int applet_no, char **argv) | 95 | int FAST_FUNC run_nofork_applet(int applet_no, char **argv) |
| 91 | { | 96 | { |
| 92 | int rc, argc; | 97 | int rc, argc; |
| 98 | struct nofork_save_area old; | ||
| 99 | |||
| 100 | save_nofork_data(&old); | ||
| 93 | 101 | ||
| 94 | applet_name = APPLET_NAME(applet_no); | 102 | applet_name = APPLET_NAME(applet_no); |
| 95 | 103 | ||
| 96 | xfunc_error_retval = EXIT_FAILURE; | 104 | xfunc_error_retval = EXIT_FAILURE; |
| 97 | 105 | ||
| 98 | /* Special flag for xfunc_die(). If xfunc will "die" | ||
| 99 | * in NOFORK applet, xfunc_die() sees negative | ||
| 100 | * die_sleep and longjmp here instead. */ | ||
| 101 | die_sleep = -1; | ||
| 102 | |||
| 103 | /* In case getopt() or getopt32() was already called: | 106 | /* In case getopt() or getopt32() was already called: |
| 104 | * reset the libc getopt() function, which keeps internal state. | 107 | * reset the libc getopt() function, which keeps internal state. |
| 105 | * | 108 | * |
| @@ -129,6 +132,11 @@ int FAST_FUNC run_nofork_applet_prime(struct nofork_save_area *old, int applet_n | |||
| 129 | while (argv[argc]) | 132 | while (argv[argc]) |
| 130 | argc++; | 133 | argc++; |
| 131 | 134 | ||
| 135 | /* Special flag for xfunc_die(). If xfunc will "die" | ||
| 136 | * in NOFORK applet, xfunc_die() sees negative | ||
| 137 | * die_sleep and longjmp here instead. */ | ||
| 138 | die_sleep = -1; | ||
| 139 | |||
| 132 | rc = setjmp(die_jmp); | 140 | rc = setjmp(die_jmp); |
| 133 | if (!rc) { | 141 | if (!rc) { |
| 134 | /* Some callers (xargs) | 142 | /* Some callers (xargs) |
| @@ -137,15 +145,6 @@ int FAST_FUNC run_nofork_applet_prime(struct nofork_save_area *old, int applet_n | |||
| 137 | memcpy(tmp_argv, argv, (argc+1) * sizeof(tmp_argv[0])); | 145 | memcpy(tmp_argv, argv, (argc+1) * sizeof(tmp_argv[0])); |
| 138 | /* Finally we can call NOFORK applet's main() */ | 146 | /* Finally we can call NOFORK applet's main() */ |
| 139 | rc = applet_main[applet_no](argc, tmp_argv); | 147 | rc = applet_main[applet_no](argc, tmp_argv); |
| 140 | |||
| 141 | /* The whole reason behind nofork_save_area is that <applet>_main | ||
| 142 | * may exit non-locally! For example, in hush Ctrl-Z tries | ||
| 143 | * (modulo bugs) to dynamically create a child (backgrounded task) | ||
| 144 | * if it detects that Ctrl-Z was pressed when a NOFORK was running. | ||
| 145 | * Testcase: interactive "rm -i". | ||
| 146 | * Don't fool yourself into thinking "and <applet>_main() returns | ||
| 147 | * quickly here" and removing "useless" nofork_save_area code. */ | ||
| 148 | |||
| 149 | } else { /* xfunc died in NOFORK applet */ | 148 | } else { /* xfunc died in NOFORK applet */ |
| 150 | /* in case they meant to return 0... */ | 149 | /* in case they meant to return 0... */ |
| 151 | if (rc == -2222) | 150 | if (rc == -2222) |
| @@ -153,7 +152,7 @@ int FAST_FUNC run_nofork_applet_prime(struct nofork_save_area *old, int applet_n | |||
| 153 | } | 152 | } |
| 154 | 153 | ||
| 155 | /* Restoring some globals */ | 154 | /* Restoring some globals */ |
| 156 | restore_nofork_data(old); | 155 | restore_nofork_data(&old); |
| 157 | 156 | ||
| 158 | /* Other globals can be simply reset to defaults */ | 157 | /* Other globals can be simply reset to defaults */ |
| 159 | #ifdef __GLIBC__ | 158 | #ifdef __GLIBC__ |
| @@ -164,15 +163,6 @@ int FAST_FUNC run_nofork_applet_prime(struct nofork_save_area *old, int applet_n | |||
| 164 | 163 | ||
| 165 | return rc & 0xff; /* don't confuse people with "exitcodes" >255 */ | 164 | return rc & 0xff; /* don't confuse people with "exitcodes" >255 */ |
| 166 | } | 165 | } |
| 167 | |||
| 168 | int FAST_FUNC run_nofork_applet(int applet_no, char **argv) | ||
| 169 | { | ||
| 170 | struct nofork_save_area old; | ||
| 171 | |||
| 172 | /* Saving globals */ | ||
| 173 | save_nofork_data(&old); | ||
| 174 | return run_nofork_applet_prime(&old, applet_no, argv); | ||
| 175 | } | ||
| 176 | #endif /* FEATURE_PREFER_APPLETS */ | 166 | #endif /* FEATURE_PREFER_APPLETS */ |
| 177 | 167 | ||
| 178 | int FAST_FUNC spawn_and_wait(char **argv) | 168 | int FAST_FUNC spawn_and_wait(char **argv) |
