aboutsummaryrefslogtreecommitdiff
path: root/init.c
diff options
context:
space:
mode:
Diffstat (limited to 'init.c')
-rw-r--r--init.c85
1 files changed, 39 insertions, 46 deletions
diff --git a/init.c b/init.c
index be04ec34f..116d07954 100644
--- a/init.c
+++ b/init.c
@@ -61,8 +61,7 @@
61#define VT_LOG "/dev/tty3" /* Virtual console */ 61#define VT_LOG "/dev/tty3" /* Virtual console */
62#define SERIAL_CON0 "/dev/ttyS0" /* Primary serial console */ 62#define SERIAL_CON0 "/dev/ttyS0" /* Primary serial console */
63#define SERIAL_CON1 "/dev/ttyS1" /* Serial console */ 63#define SERIAL_CON1 "/dev/ttyS1" /* Serial console */
64#define SHELL "/bin/sh" /* Default shell */ 64#define SHELL "-sh" /* Default shell */
65#define REBOOT "/sbin/reboot" /* Default ctrl-alt-del command */
66#define INITTAB "/etc/inittab" /* inittab file location */ 65#define INITTAB "/etc/inittab" /* inittab file location */
67#define INIT_SCRIPT "/etc/init.d/rcS" /* Default sysinit script. */ 66#define INIT_SCRIPT "/etc/init.d/rcS" /* Default sysinit script. */
68 67
@@ -72,7 +71,6 @@
72/* Allowed init action types */ 71/* Allowed init action types */
73typedef enum { 72typedef enum {
74 SYSINIT=1, 73 SYSINIT=1,
75 CTRLALTDEL,
76 RESPAWN, 74 RESPAWN,
77 ASKFIRST, 75 ASKFIRST,
78 WAIT, 76 WAIT,
@@ -87,7 +85,6 @@ typedef struct initActionType{
87 85
88static const struct initActionType actions[] = { 86static const struct initActionType actions[] = {
89 {"sysinit", SYSINIT}, 87 {"sysinit", SYSINIT},
90 {"ctrlaltdel", CTRLALTDEL},
91 {"respawn", RESPAWN}, 88 {"respawn", RESPAWN},
92 {"askfirst", ASKFIRST}, 89 {"askfirst", ASKFIRST},
93 {"wait", WAIT}, 90 {"wait", WAIT},
@@ -326,15 +323,18 @@ static int waitfor(int pid)
326{ 323{
327 int status, wpid; 324 int status, wpid;
328 325
329 message(LOG, "Waiting for process %d.\n", pid); 326 while (1) {
330 while ((wpid = wait(&status)) != pid) { 327 wpid = wait(&status);
331 if (wpid > 0) 328 if (wpid > 0 ) {
332 message(LOG, "pid %d exited, status=0x%x.\n", wpid, status); 329 message(LOG, "pid %d exited, status=0x%x.\n", wpid, status);
330 break;
331 }
332 if (wpid == pid )
333 break;
333 } 334 }
334 return wpid; 335 return wpid;
335} 336}
336 337
337
338static pid_t run(char* command, 338static pid_t run(char* command,
339 char *terminal, int get_enter) 339 char *terminal, int get_enter)
340{ 340{
@@ -346,27 +346,32 @@ static pid_t run(char* command,
346 "\nPlease press Enter to activate this console. "; 346 "\nPlease press Enter to activate this console. ";
347 347
348 if ((pid = fork()) == 0) { 348 if ((pid = fork()) == 0) {
349 int fd; 349 pid_t shell_pgid = getpid ();
350
350 /* Clean up */ 351 /* Clean up */
351 close(0); 352 close(0);
352 close(1); 353 close(1);
353 close(2); 354 close(2);
354 setsid(); 355 setsid();
355 356
357 if (device_open(terminal, O_RDWR) < 0) {
358 message(LOG|CONSOLE, "Bummer, can't open %s\r\n", terminal);
359 exit(1);
360 }
361 dup(0);
362 dup(0);
363 /* Grab control of the terminal. */
364 if (tcsetpgrp (0, getpgrp()) < 0) {
365 message(LOG|CONSOLE, "tcsetpgrp error: %s\r\n", strerror(errno));
366 }
367 set_term(0);
368
356 /* Reset signal handlers set for parent process */ 369 /* Reset signal handlers set for parent process */
357 signal(SIGUSR1, SIG_DFL); 370 signal(SIGUSR1, SIG_DFL);
358 signal(SIGUSR2, SIG_DFL); 371 signal(SIGUSR2, SIG_DFL);
359 signal(SIGINT, SIG_DFL); 372 signal(SIGINT, SIG_DFL);
360 signal(SIGTERM, SIG_DFL); 373 signal(SIGTERM, SIG_DFL);
361 374
362 if ((fd = device_open(terminal, O_RDWR)) < 0) {
363 message(LOG|CONSOLE, "Bummer, can't open %s\r\n", terminal);
364 exit(-1);
365 }
366 dup(fd);
367 dup(fd);
368 tcsetpgrp(0, getpgrp());
369 set_term(0);
370 375
371 if (get_enter==TRUE) { 376 if (get_enter==TRUE) {
372 /* 377 /*
@@ -379,7 +384,7 @@ static pid_t run(char* command,
379 */ 384 */
380 char c; 385 char c;
381 message(LOG, "Waiting for enter to start '%s' (pid %d, console %s)\r\n", 386 message(LOG, "Waiting for enter to start '%s' (pid %d, console %s)\r\n",
382 command, getpid(), terminal ); 387 command, shell_pgid, terminal );
383 write(fileno(stdout), press_enter, sizeof(press_enter) - 1); 388 write(fileno(stdout), press_enter, sizeof(press_enter) - 1);
384 read(fileno(stdin), &c, 1); 389 read(fileno(stdin), &c, 1);
385 } 390 }
@@ -396,7 +401,7 @@ static pid_t run(char* command,
396 401
397 /* Log the process name and args */ 402 /* Log the process name and args */
398 message(LOG, "Starting pid %d, console %s: '%s'\r\n", 403 message(LOG, "Starting pid %d, console %s: '%s'\r\n",
399 getpid(), terminal, cmd[0]); 404 shell_pgid, terminal, cmd[0]);
400 405
401 /* Now run it. The new program will take over this PID, 406 /* Now run it. The new program will take over this PID,
402 * so nothing further in init.c should be run. */ 407 * so nothing further in init.c should be run. */
@@ -488,16 +493,6 @@ static void reboot_signal(int sig)
488 exit(0); 493 exit(0);
489} 494}
490 495
491static void ctrl_alt_del_signal(int sig)
492{
493 initAction* a;
494 /* Run whatever we are supposed to run */
495 for( a=initActionList ; a; a=a->nextPtr) {
496 if (a->action == CTRLALTDEL) {
497 waitfor(run(a->process, console, FALSE));
498 }
499 }
500}
501#endif 496#endif
502 497
503void new_initAction (const struct initActionType *a, 498void new_initAction (const struct initActionType *a,
@@ -547,8 +542,6 @@ void parse_inittab(void)
547 /* Askfirst shell on tty2 */ 542 /* Askfirst shell on tty2 */
548 if (second_console != NULL) 543 if (second_console != NULL)
549 new_initAction( &(actions[3]), SHELL, second_console ); 544 new_initAction( &(actions[3]), SHELL, second_console );
550 /* Control-alt-del */
551 new_initAction( &(actions[1]), REBOOT, console );
552 /* sysinit */ 545 /* sysinit */
553 new_initAction( &(actions[0]), INIT_SCRIPT, console ); 546 new_initAction( &(actions[0]), INIT_SCRIPT, console );
554 547
@@ -614,8 +607,6 @@ extern int init_main(int argc, char **argv)
614 initAction *a; 607 initAction *a;
615 pid_t wpid; 608 pid_t wpid;
616 int status; 609 int status;
617 int single = FALSE;
618
619 610
620#ifndef DEBUG_INIT 611#ifndef DEBUG_INIT
621 /* Expect to be PID 1 iff we are run as init (not linuxrc) */ 612 /* Expect to be PID 1 iff we are run as init (not linuxrc) */
@@ -624,10 +615,13 @@ extern int init_main(int argc, char **argv)
624 "This version of init is designed to be run only by the kernel\n"); 615 "This version of init is designed to be run only by the kernel\n");
625 } 616 }
626 617
618 /* from the controlling terminal */
619 setsid();
620
627 /* Set up sig handlers -- be sure to clear all of these in run() */ 621 /* Set up sig handlers -- be sure to clear all of these in run() */
628 signal(SIGUSR1, halt_signal); 622 signal(SIGUSR1, halt_signal);
629 signal(SIGUSR2, reboot_signal); 623 signal(SIGUSR2, reboot_signal);
630 signal(SIGINT, ctrl_alt_del_signal); 624 signal(SIGINT, reboot_signal);
631 signal(SIGTERM, reboot_signal); 625 signal(SIGTERM, reboot_signal);
632 626
633 /* Turn off rebooting via CTL-ALT-DEL -- we get a 627 /* Turn off rebooting via CTL-ALT-DEL -- we get a
@@ -643,7 +637,6 @@ extern int init_main(int argc, char **argv)
643 close(1); 637 close(1);
644 close(2); 638 close(2);
645 set_term(0); 639 set_term(0);
646 setsid();
647 640
648 /* Make sure PATH is set to something sane */ 641 /* Make sure PATH is set to something sane */
649 putenv(_PATH_STDPATH); 642 putenv(_PATH_STDPATH);
@@ -673,8 +666,8 @@ extern int init_main(int argc, char **argv)
673 666
674 /* Check if we are supposed to be in single user mode */ 667 /* Check if we are supposed to be in single user mode */
675 if ( argc > 1 && (!strcmp(argv[1], "single") || 668 if ( argc > 1 && (!strcmp(argv[1], "single") ||
676 !strcmp(argv[1], "-s") || !strcmp(argv[1], "1"))) { 669 !strcmp(argv[1], "-s") || !strcmp(argv[1], "1")))
677 single = TRUE; 670 {
678 /* Ask first then start a shell on tty2 */ 671 /* Ask first then start a shell on tty2 */
679 if (second_console != NULL) 672 if (second_console != NULL)
680 new_initAction( &(actions[3]), SHELL, second_console); 673 new_initAction( &(actions[3]), SHELL, second_console);
@@ -687,7 +680,7 @@ extern int init_main(int argc, char **argv)
687 680
688 /* Now run everything that needs to be run */ 681 /* Now run everything that needs to be run */
689 682
690 /* First run sysinit */ 683 /* First run the sysinit command */
691 for( a=initActionList ; a; a=a->nextPtr) { 684 for( a=initActionList ; a; a=a->nextPtr) {
692 if (a->action == SYSINIT) { 685 if (a->action == SYSINIT) {
693 waitfor(run(a->process, console, FALSE)); 686 waitfor(run(a->process, console, FALSE));
@@ -712,8 +705,8 @@ extern int init_main(int argc, char **argv)
712 } 705 }
713 } 706 }
714 707
715 /* Now run the looping stuff */ 708 /* Now run the looping stuff for the rest of forever */
716 for (;;) { 709 while (1) {
717 for( a=initActionList ; a; a=a->nextPtr) { 710 for( a=initActionList ; a; a=a->nextPtr) {
718 /* Only run stuff with pid==0. If they have 711 /* Only run stuff with pid==0. If they have
719 * a pid, that means they are still running */ 712 * a pid, that means they are still running */
@@ -725,26 +718,26 @@ extern int init_main(int argc, char **argv)
725 break; 718 break;
726 case ASKFIRST: 719 case ASKFIRST:
727 /* run the askfirst stuff */ 720 /* run the askfirst stuff */
728 a->pid = waitfor(run(a->process, console, TRUE)); 721 a->pid = run(a->process, console, TRUE);
729 break; 722 break;
730 /* silence the compiler's whining */ 723 /* silence the compiler's incessant whining */
731 default: 724 default:
732 break; 725 break;
733 } 726 }
734 } 727 }
735 } 728 }
736 729 /* Wait for a child process to exit */
737 wpid = wait(&status); 730 wpid = wait(&status);
738 /* Find out who died and clean up their corpse */
739 if (wpid > 0 ) { 731 if (wpid > 0 ) {
740 message(LOG, "pid %d exited, status=%x.\n", wpid, status); 732 /* Find out who died and clean up their corpse */
741 for( a=initActionList ; a; a=a->nextPtr) { 733 for( a=initActionList ; a; a=a->nextPtr) {
742 if (a->pid==wpid) { 734 if (a->pid==wpid) {
743 a->pid=0; 735 a->pid=0;
736 message(LOG, "Process '%s' (pid %d) exited. Scheduling it for restart.\n",
737 a->process, wpid);
744 } 738 }
745 } 739 }
746 } 740 }
747
748 sleep(1); 741 sleep(1);
749 } 742 }
750} 743}