aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRon Yorston <rmy@pobox.com>2020-06-09 16:25:49 +0100
committerRon Yorston <rmy@pobox.com>2020-06-09 16:25:49 +0100
commit4fe76647b356a85810fa3d355d7ad0512be1210c (patch)
tree80f760e239a2013aadaecfc92ad7652129bd3ebf
parent0656b8730855833567bf305b930442f50cbd44b4 (diff)
downloadbusybox-w32-4fe76647b356a85810fa3d355d7ad0512be1210c.tar.gz
busybox-w32-4fe76647b356a85810fa3d355d7ad0512be1210c.tar.bz2
busybox-w32-4fe76647b356a85810fa3d355d7ad0512be1210c.zip
ash: minimise work when a forkshell process is started
There's no need to create or initialise the global data structures when a forkshell is being started: they'll soon be replaced by data from the forkshell data block. Move the call to forkshell_init() to the top of ash_main() along with some initialisation that's common to forkshell shells and ordinary shells. Add the minimum necessary initialisation to forkshell_init().
-rw-r--r--shell/ash.c46
1 files changed, 27 insertions, 19 deletions
diff --git a/shell/ash.c b/shell/ash.c
index f57819810..e21131b01 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -391,7 +391,6 @@ enum {
391 391
392static struct forkshell* forkshell_prepare(struct forkshell *fs); 392static struct forkshell* forkshell_prepare(struct forkshell *fs);
393static void forkshell_init(const char *idstr); 393static void forkshell_init(const char *idstr);
394static void forkshell_child(struct forkshell *fs);
395static void sticky_free(void *p); 394static void sticky_free(void *p);
396# define free(p) sticky_free(p) 395# define free(p) sticky_free(p)
397#if !JOBS 396#if !JOBS
@@ -15254,12 +15253,27 @@ int ash_main(int argc UNUSED_PARAM, char **argv)
15254 int login_sh; 15253 int login_sh;
15255#if ENABLE_PLATFORM_MINGW32 15254#if ENABLE_PLATFORM_MINGW32
15256 char *sd; 15255 char *sd;
15257 int is_forkshell; 15256
15257 INIT_G_memstack();
15258
15259 /* from init() */
15260 basepf.next_to_pgetc = basepf.buf = ckmalloc(IBUFSIZ);
15261 basepf.linno = 1;
15262
15263 hSIGINT = CreateEvent(NULL, TRUE, FALSE, NULL);
15264
15265 if (argc == 3 && !strcmp(argv[1], "--fs")) {
15266 forkshell_init(argv[2]);
15267 /* only reached in case of error */
15268 bb_error_msg_and_die("forkshell failed");
15269 }
15258#endif 15270#endif
15259 15271
15260 /* Initialize global data */ 15272 /* Initialize global data */
15261 INIT_G_misc(); 15273 INIT_G_misc();
15274#if !ENABLE_PLATFORM_MINGW32
15262 INIT_G_memstack(); 15275 INIT_G_memstack();
15276#endif
15263 INIT_G_var(); 15277 INIT_G_var();
15264#if ENABLE_ASH_ALIAS 15278#if ENABLE_ASH_ALIAS
15265 INIT_G_alias(); 15279 INIT_G_alias();
@@ -15303,27 +15317,13 @@ int ash_main(int argc UNUSED_PARAM, char **argv)
15303 rootpid = getpid(); 15317 rootpid = getpid();
15304 15318
15305#if ENABLE_PLATFORM_MINGW32 15319#if ENABLE_PLATFORM_MINGW32
15306 /* we will never free this */
15307 basepf.next_to_pgetc = basepf.buf = ckmalloc(IBUFSIZ);
15308 basepf.linno = 1;
15309
15310 winxp = (argv[1] != NULL && strcmp(argv[1], "-X") == 0); 15320 winxp = (argv[1] != NULL && strcmp(argv[1], "-X") == 0);
15311 is_forkshell = (argc == 3 && !strcmp(argv[1], "--fs"));
15312 if (!is_forkshell)
15313#endif 15321#endif
15314 init(); 15322 init();
15315 setstackmark(&smark); 15323 setstackmark(&smark);
15316 15324
15317#if ENABLE_PLATFORM_MINGW32 15325#if ENABLE_PLATFORM_MINGW32
15318 hSIGINT = CreateEvent(NULL, TRUE, FALSE, NULL);
15319 SetConsoleCtrlHandler(ctrl_handler, TRUE); 15326 SetConsoleCtrlHandler(ctrl_handler, TRUE);
15320
15321 if (is_forkshell) {
15322 forkshell_init(argv[2]);
15323
15324 /* only reached in case of error */
15325 bb_error_msg_and_die("forkshell failed");
15326 }
15327#endif 15327#endif
15328 15328
15329#if NUM_SCRIPTS > 0 15329#if NUM_SCRIPTS > 0
@@ -16301,7 +16301,6 @@ forkshell_prepare(struct forkshell *fs)
16301 return new; 16301 return new;
16302} 16302}
16303 16303
16304#undef exception_handler
16305#undef trap 16304#undef trap
16306#undef trap_ptr 16305#undef trap_ptr
16307static void *sticky_mem_start, *sticky_mem_end; 16306static void *sticky_mem_start, *sticky_mem_end;
@@ -16316,6 +16315,7 @@ forkshell_init(const char *idstr)
16316 int i; 16315 int i;
16317 char **ptr; 16316 char **ptr;
16318 char *lrelocate; 16317 char *lrelocate;
16318 struct jmploc jmploc;
16319 16319
16320 if (sscanf(idstr, "%p", &map_handle) != 1) 16320 if (sscanf(idstr, "%p", &map_handle) != 1)
16321 return; 16321 return;
@@ -16348,11 +16348,10 @@ forkshell_init(const char *idstr)
16348 e = e->next; 16348 e = e->next;
16349 } 16349 }
16350 } 16350 }
16351 fs->gmp->exception_handler = ash_ptr_to_globals_misc->exception_handler;
16352 memset(fs->gmp->trap, 0, sizeof(fs->gmp->trap[0])*NSIG); 16351 memset(fs->gmp->trap, 0, sizeof(fs->gmp->trap[0])*NSIG);
16353 /* fs->gmp->trap_ptr = fs->gmp->trap; */ 16352 /* fs->gmp->trap_ptr = fs->gmp->trap; */
16354 16353
16355 /* Switch global variables */ 16354 /* Set global variables */
16356 gvpp = (struct globals_var **)&ash_ptr_to_globals_var; 16355 gvpp = (struct globals_var **)&ash_ptr_to_globals_var;
16357 *gvpp = fs->gvp; 16356 *gvpp = fs->gvp;
16358 gmpp = (struct globals_misc **)&ash_ptr_to_globals_misc; 16357 gmpp = (struct globals_misc **)&ash_ptr_to_globals_misc;
@@ -16374,6 +16373,12 @@ forkshell_init(const char *idstr)
16374 16373
16375 reinitvar(); 16374 reinitvar();
16376 16375
16376 if (setjmp(jmploc.loc)) {
16377 exitreset();
16378 exitshell();
16379 }
16380 exception_handler = &jmploc;
16381
16377 shlvl++; 16382 shlvl++;
16378 if (fs->mode == FORK_BG) { 16383 if (fs->mode == FORK_BG) {
16379 SetConsoleCtrlHandler(NULL, TRUE); 16384 SetConsoleCtrlHandler(NULL, TRUE);
@@ -16383,6 +16388,9 @@ forkshell_init(const char *idstr)
16383 ash_msg_and_raise_perror("can't open '%s'", bb_dev_null); 16388 ash_msg_and_raise_perror("can't open '%s'", bb_dev_null);
16384 } 16389 }
16385 } 16390 }
16391 else {
16392 SetConsoleCtrlHandler(ctrl_handler, TRUE);
16393 }
16386 forkshell_child(fs); 16394 forkshell_child(fs);
16387} 16395}
16388 16396