From 983b51b17bb36e5b77cb160abdfbcf9d25675dd9 Mon Sep 17 00:00:00 2001 From: Erik Andersen Date: Tue, 4 Apr 2000 18:14:25 +0000 Subject: minor changes to mount/umount to support-by-ignoring the "-v" flag. Added optional core dumping as a feature for init, and include a rewrite of syslogd so that it now supports multiple concurrent connections. -Erik --- init.c | 24 +++++- init/init.c | 24 +++++- mount.c | 1 + sysklogd/syslogd.c | 238 +++++++++++++++++++++++++++++++++------------------- syslogd.c | 238 +++++++++++++++++++++++++++++++++------------------- umount.c | 2 + util-linux/mount.c | 1 + util-linux/umount.c | 2 + 8 files changed, 354 insertions(+), 176 deletions(-) diff --git a/init.c b/init.c index 907916537..f327a52af 100644 --- a/init.c +++ b/init.c @@ -45,7 +45,7 @@ #include #include /* For check_free_memory() */ #ifdef BB_SYSLOGD -#include +# include #endif #include #include @@ -54,6 +54,15 @@ #include #include + +/* + * When CORE_ENABLE_FLAG_FILE exists, setrlimit is called before + * process is spawned to set corelimit to unlimited. + */ +#define CORE_ENABLE_FLAG_FILE "/.init_enable_core" +#include +#include + #ifndef KERNEL_VERSION #define KERNEL_VERSION(a,b,c) (((a) << 16) + ((b) << 8) + (c)) #endif @@ -406,6 +415,16 @@ static pid_t run(char *command, char *terminal, int get_enter) cmd[i] = NULL; } + { + struct stat sb; + if (stat (CORE_ENABLE_FLAG_FILE, &sb) == 0) { + struct rlimit limit; + limit.rlim_cur = RLIM_INFINITY; + limit.rlim_max = RLIM_INFINITY; + setrlimit(RLIMIT_CORE, &limit); + } + } + /* Now run it. The new program will take over this PID, * so nothing further in init.c should be run. */ execve(cmd[0], cmd, environment); @@ -836,6 +855,7 @@ extern int init_main(int argc, char **argv) close(1); close(2); set_term(0); + chdir("/"); setsid(); /* Make sure PATH is set to something sane */ @@ -881,7 +901,7 @@ extern int init_main(int argc, char **argv) * of "askfirst" shells */ parse_inittab(); } - + /* Fix up argv[0] to be certain we claim to be init */ strncpy(argv[0], "init", strlen(argv[0])+1); if (argc > 1) diff --git a/init/init.c b/init/init.c index 907916537..f327a52af 100644 --- a/init/init.c +++ b/init/init.c @@ -45,7 +45,7 @@ #include #include /* For check_free_memory() */ #ifdef BB_SYSLOGD -#include +# include #endif #include #include @@ -54,6 +54,15 @@ #include #include + +/* + * When CORE_ENABLE_FLAG_FILE exists, setrlimit is called before + * process is spawned to set corelimit to unlimited. + */ +#define CORE_ENABLE_FLAG_FILE "/.init_enable_core" +#include +#include + #ifndef KERNEL_VERSION #define KERNEL_VERSION(a,b,c) (((a) << 16) + ((b) << 8) + (c)) #endif @@ -406,6 +415,16 @@ static pid_t run(char *command, char *terminal, int get_enter) cmd[i] = NULL; } + { + struct stat sb; + if (stat (CORE_ENABLE_FLAG_FILE, &sb) == 0) { + struct rlimit limit; + limit.rlim_cur = RLIM_INFINITY; + limit.rlim_max = RLIM_INFINITY; + setrlimit(RLIMIT_CORE, &limit); + } + } + /* Now run it. The new program will take over this PID, * so nothing further in init.c should be run. */ execve(cmd[0], cmd, environment); @@ -836,6 +855,7 @@ extern int init_main(int argc, char **argv) close(1); close(2); set_term(0); + chdir("/"); setsid(); /* Make sure PATH is set to something sane */ @@ -881,7 +901,7 @@ extern int init_main(int argc, char **argv) * of "askfirst" shells */ parse_inittab(); } - + /* Fix up argv[0] to be certain we claim to be init */ strncpy(argv[0], "init", strlen(argv[0])+1); if (argc > 1) diff --git a/mount.c b/mount.c index 30a060fc1..329c07780 100644 --- a/mount.c +++ b/mount.c @@ -418,6 +418,7 @@ extern int mount_main(int argc, char **argv) break; #endif case 'v': + break; /* ignore -v */ case 'h': case '-': goto goodbye; diff --git a/sysklogd/syslogd.c b/sysklogd/syslogd.c index 4bc1d3d72..464d7846e 100644 --- a/sysklogd/syslogd.c +++ b/sysklogd/syslogd.c @@ -22,21 +22,21 @@ */ #include "internal.h" -#include +#include +#include +#include +#include +#include +#include #include +#include +#include #include +#include +#include #include -#include #include -#include -#include -#include -#include -#include -#include -#include -#include -#include +#include #define ksyslog klogctl extern int ksyslog(int type, char *buf, int len); @@ -47,8 +47,10 @@ extern int ksyslog(int type, char *buf, int len); #include /* Path for the file where all log messages are written */ -#define __LOG_FILE "/var/log/messages" +#define __LOG_FILE "/var/log/messages" +/* Path to the unix socket */ +char lfile[PATH_MAX] = ""; static char *logFilePath = __LOG_FILE; @@ -70,9 +72,8 @@ static const char syslogd_usage[] = #endif "\t-O\tSpecify an alternate log file. default=/var/log/messages\n"; - /* Note: There is also a function called "message()" in init.c */ -/* print a message to the log file */ +/* Print a message to the log file. */ static void message(char *fmt, ...) { int fd; @@ -145,7 +146,7 @@ static void logMessage(int pri, char *msg) static void quit_signal(int sig) { logMessage(0, "System log daemon exiting."); - unlink(_PATH_LOG); + unlink(lfile); exit(TRUE); } @@ -157,88 +158,134 @@ static void domark(int sig) } } -static void doSyslogd(void) +static void doSyslogd (void) __attribute__ ((noreturn)); +static void doSyslogd (void) { struct sockaddr_un sunx; - int fd, conn; size_t addrLength; - char buf[1024]; - char *q, *p = buf; - int readSize; + int sock_fd; + fd_set readfds; + char lfile[PATH_MAX]; + int t = readlink(_PATH_LOG, lfile, sizeof(lfile) - 1); /* Resolve symlinks */ /* Set up sig handlers */ - signal(SIGINT, quit_signal); - signal(SIGTERM, quit_signal); - signal(SIGQUIT, quit_signal); - signal(SIGALRM, domark); - signal(SIGHUP, SIG_IGN); - alarm(MarkInterval); - - /* Remove any preexisting socket/file */ - unlink(_PATH_LOG); - - memset(&sunx, 0, sizeof(sunx)); - sunx.sun_family = AF_UNIX; /* Unix domain socket */ - strncpy(sunx.sun_path, _PATH_LOG, sizeof(sunx.sun_path)); - if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) { - perror("Couldn't obtain descriptor for socket " _PATH_LOG); - exit(FALSE); + signal (SIGINT, quit_signal); + signal (SIGTERM, quit_signal); + signal (SIGQUIT, quit_signal); + signal (SIGHUP, SIG_IGN); + signal (SIGALRM, domark); + alarm (MarkInterval); + + if (t == -1) + strncpy(lfile, _PATH_LOG, sizeof(lfile)); + else + lfile[t] = '\0'; + + unlink (lfile); + + memset (&sunx, 0, sizeof(sunx)); + + sunx.sun_family = AF_UNIX; + strncpy (sunx.sun_path, lfile, sizeof(sunx.sun_path)); + if ((sock_fd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) { + perror ("Couldn't obtain descriptor for socket " _PATH_LOG); + exit (FALSE); } - addrLength = sizeof(sunx.sun_family) + strlen(sunx.sun_path); - if ((bind(fd, (struct sockaddr *) &sunx, addrLength)) || - (listen(fd, 5))) { - perror("Could not connect to socket " _PATH_LOG); - exit(FALSE); + addrLength = sizeof (sunx.sun_family) + strlen (sunx.sun_path); + if ((bind (sock_fd, (struct sockaddr *) &sunx, addrLength)) || + (listen (sock_fd, 5))) { + perror ("Could not connect to socket " _PATH_LOG); + exit (FALSE); } - umask(0); - if (chmod(_PATH_LOG, 0666) < 0) { - perror("Could not set permission on " _PATH_LOG); - exit(FALSE); + if (chmod (lfile, 0666) < 0) { + perror ("Could not set permission on " _PATH_LOG); + exit (FALSE); } - logMessage(0, "syslogd started: BusyBox v" BB_VER " (" BB_BT ")"); - - - while ((conn = accept(fd, (struct sockaddr *) &sunx, - &addrLength)) >= 0) { - while ((readSize = read(conn, buf, sizeof(buf))) > 0) { - char line[1025]; - unsigned char c; - int pri = (LOG_USER | LOG_NOTICE); - - memset(line, 0, sizeof(line)); - p = buf; - q = line; - while (p && (c = *p) && q < &line[sizeof(line) - 1]) { - if (c == '<') { - /* Parse the magic priority number */ - pri = 0; - while (isdigit(*(++p))) { - pri = 10 * pri + (*p - '0'); + FD_ZERO (&readfds); + FD_SET (sock_fd, &readfds); + + logMessage (0, "syslogd started: BusyBox v" BB_VER " (" BB_BT ")"); + + for (;;) { + int n_ready; + int fd; + + if ((n_ready = select (FD_SETSIZE, &readfds, NULL, NULL, NULL)) < 0) { + if (errno == EINTR) continue; /* alarm may have happened. */ + perror ("select"); + exit (FALSE); + } + + /* Skip stdin, stdout, stderr */ + for (fd = 3; fd <= FD_SETSIZE; fd++) { + if (FD_ISSET (fd, &readfds)) { + if (fd == sock_fd) { + int conn; + if ((conn = accept(sock_fd, (struct sockaddr *) &sunx, + &addrLength)) < 0) { + perror ("accept"); + exit (FALSE); /* #### ??? */ } - if (pri & ~(LOG_FACMASK | LOG_PRIMASK)) - pri = (LOG_USER | LOG_NOTICE); - } else if (c == '\n') { - *q++ = ' '; - } else if (iscntrl(c) && (c < 0177)) { - *q++ = '^'; - *q++ = c ^ 0100; - } else { - *q++ = c; + FD_SET (conn, &readfds); } - p++; - } - *q = '\0'; + else { +#define BUFSIZE 1024 + 1 + char buf[BUFSIZE]; + char *q, *p; + int n_read; - /* Now log it */ - logMessage(pri, line); + n_read = read (fd, buf, BUFSIZE); + + if (n_read < 0) { + perror ("read error"); + goto close_fd; + } + else if (n_read > 0) { + char line[BUFSIZE]; + unsigned char c; + int pri = (LOG_USER | LOG_NOTICE); + + memset (line, 0, sizeof(line)); + p = buf; + q = line; + while (p && (c = *p) && q < &line[sizeof(line) - 1]) { + if (c == '<') { + /* Parse the magic priority number */ + pri = 0; + while (isdigit(*(++p))) { + pri = 10 * pri + (*p - '0'); + } + if (pri & ~(LOG_FACMASK | LOG_PRIMASK)) + pri = (LOG_USER | LOG_NOTICE); + } else if (c == '\n') { + *q++ = ' '; + } else if (iscntrl(c) && (c < 0177)) { + *q++ = '^'; + *q++ = c ^ 0100; + } else { + *q++ = c; + } + p++; + } + *q = '\0'; + + /* Now log it */ + logMessage(pri, line); + + close_fd: + close (fd); + FD_CLR (fd, &readfds); + } + else { /* EOF */ + goto close_fd; + } + } + } } - close(conn); } - - close(fd); } #ifdef BB_KLOGD @@ -251,7 +298,8 @@ static void klogd_signal(int sig) exit(TRUE); } -static void doKlogd(void) +static void doKlogd (void) __attribute__ ((noreturn)); +static void doKlogd (void) { int priority = LOG_INFO; char log_buffer[4096]; @@ -317,6 +365,16 @@ static void doKlogd(void) #endif +static void daemon_init (char **argv, char *dz, void fn (void)) __attribute__ ((noreturn)); +static void daemon_init (char **argv, char *dz, void fn (void)) +{ + setsid(); + chdir ("/"); + strncpy(argv[0], dz, strlen(argv[0])); + fn(); + exit(0); +} + extern int syslogd_main(int argc, char **argv) { int pid, klogd_pid; @@ -366,13 +424,14 @@ extern int syslogd_main(int argc, char **argv) *p++ = '\0'; } + umask(0); + #ifdef BB_KLOGD /* Start up the klogd process */ if (startKlogd == TRUE) { klogd_pid = fork(); if (klogd_pid == 0) { - strncpy(argv[0], "klogd", strlen(argv[0])); - doKlogd(); + daemon_init (argv, "klogd", doKlogd); } } #endif @@ -382,8 +441,7 @@ extern int syslogd_main(int argc, char **argv) if (pid < 0) exit(pid); else if (pid == 0) { - strncpy(argv[0], "syslogd", strlen(argv[0])); - doSyslogd(); + daemon_init (argv, "syslogd", doSyslogd); } } else { doSyslogd(); @@ -391,3 +449,11 @@ extern int syslogd_main(int argc, char **argv) exit(TRUE); } + +/* + * Local Variables + * c-file-style: "linux" + * c-basic-offset: 4 + * tab-width: 4 + * End: + */ diff --git a/syslogd.c b/syslogd.c index 4bc1d3d72..464d7846e 100644 --- a/syslogd.c +++ b/syslogd.c @@ -22,21 +22,21 @@ */ #include "internal.h" -#include +#include +#include +#include +#include +#include +#include #include +#include +#include #include +#include +#include #include -#include #include -#include -#include -#include -#include -#include -#include -#include -#include -#include +#include #define ksyslog klogctl extern int ksyslog(int type, char *buf, int len); @@ -47,8 +47,10 @@ extern int ksyslog(int type, char *buf, int len); #include /* Path for the file where all log messages are written */ -#define __LOG_FILE "/var/log/messages" +#define __LOG_FILE "/var/log/messages" +/* Path to the unix socket */ +char lfile[PATH_MAX] = ""; static char *logFilePath = __LOG_FILE; @@ -70,9 +72,8 @@ static const char syslogd_usage[] = #endif "\t-O\tSpecify an alternate log file. default=/var/log/messages\n"; - /* Note: There is also a function called "message()" in init.c */ -/* print a message to the log file */ +/* Print a message to the log file. */ static void message(char *fmt, ...) { int fd; @@ -145,7 +146,7 @@ static void logMessage(int pri, char *msg) static void quit_signal(int sig) { logMessage(0, "System log daemon exiting."); - unlink(_PATH_LOG); + unlink(lfile); exit(TRUE); } @@ -157,88 +158,134 @@ static void domark(int sig) } } -static void doSyslogd(void) +static void doSyslogd (void) __attribute__ ((noreturn)); +static void doSyslogd (void) { struct sockaddr_un sunx; - int fd, conn; size_t addrLength; - char buf[1024]; - char *q, *p = buf; - int readSize; + int sock_fd; + fd_set readfds; + char lfile[PATH_MAX]; + int t = readlink(_PATH_LOG, lfile, sizeof(lfile) - 1); /* Resolve symlinks */ /* Set up sig handlers */ - signal(SIGINT, quit_signal); - signal(SIGTERM, quit_signal); - signal(SIGQUIT, quit_signal); - signal(SIGALRM, domark); - signal(SIGHUP, SIG_IGN); - alarm(MarkInterval); - - /* Remove any preexisting socket/file */ - unlink(_PATH_LOG); - - memset(&sunx, 0, sizeof(sunx)); - sunx.sun_family = AF_UNIX; /* Unix domain socket */ - strncpy(sunx.sun_path, _PATH_LOG, sizeof(sunx.sun_path)); - if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) { - perror("Couldn't obtain descriptor for socket " _PATH_LOG); - exit(FALSE); + signal (SIGINT, quit_signal); + signal (SIGTERM, quit_signal); + signal (SIGQUIT, quit_signal); + signal (SIGHUP, SIG_IGN); + signal (SIGALRM, domark); + alarm (MarkInterval); + + if (t == -1) + strncpy(lfile, _PATH_LOG, sizeof(lfile)); + else + lfile[t] = '\0'; + + unlink (lfile); + + memset (&sunx, 0, sizeof(sunx)); + + sunx.sun_family = AF_UNIX; + strncpy (sunx.sun_path, lfile, sizeof(sunx.sun_path)); + if ((sock_fd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) { + perror ("Couldn't obtain descriptor for socket " _PATH_LOG); + exit (FALSE); } - addrLength = sizeof(sunx.sun_family) + strlen(sunx.sun_path); - if ((bind(fd, (struct sockaddr *) &sunx, addrLength)) || - (listen(fd, 5))) { - perror("Could not connect to socket " _PATH_LOG); - exit(FALSE); + addrLength = sizeof (sunx.sun_family) + strlen (sunx.sun_path); + if ((bind (sock_fd, (struct sockaddr *) &sunx, addrLength)) || + (listen (sock_fd, 5))) { + perror ("Could not connect to socket " _PATH_LOG); + exit (FALSE); } - umask(0); - if (chmod(_PATH_LOG, 0666) < 0) { - perror("Could not set permission on " _PATH_LOG); - exit(FALSE); + if (chmod (lfile, 0666) < 0) { + perror ("Could not set permission on " _PATH_LOG); + exit (FALSE); } - logMessage(0, "syslogd started: BusyBox v" BB_VER " (" BB_BT ")"); - - - while ((conn = accept(fd, (struct sockaddr *) &sunx, - &addrLength)) >= 0) { - while ((readSize = read(conn, buf, sizeof(buf))) > 0) { - char line[1025]; - unsigned char c; - int pri = (LOG_USER | LOG_NOTICE); - - memset(line, 0, sizeof(line)); - p = buf; - q = line; - while (p && (c = *p) && q < &line[sizeof(line) - 1]) { - if (c == '<') { - /* Parse the magic priority number */ - pri = 0; - while (isdigit(*(++p))) { - pri = 10 * pri + (*p - '0'); + FD_ZERO (&readfds); + FD_SET (sock_fd, &readfds); + + logMessage (0, "syslogd started: BusyBox v" BB_VER " (" BB_BT ")"); + + for (;;) { + int n_ready; + int fd; + + if ((n_ready = select (FD_SETSIZE, &readfds, NULL, NULL, NULL)) < 0) { + if (errno == EINTR) continue; /* alarm may have happened. */ + perror ("select"); + exit (FALSE); + } + + /* Skip stdin, stdout, stderr */ + for (fd = 3; fd <= FD_SETSIZE; fd++) { + if (FD_ISSET (fd, &readfds)) { + if (fd == sock_fd) { + int conn; + if ((conn = accept(sock_fd, (struct sockaddr *) &sunx, + &addrLength)) < 0) { + perror ("accept"); + exit (FALSE); /* #### ??? */ } - if (pri & ~(LOG_FACMASK | LOG_PRIMASK)) - pri = (LOG_USER | LOG_NOTICE); - } else if (c == '\n') { - *q++ = ' '; - } else if (iscntrl(c) && (c < 0177)) { - *q++ = '^'; - *q++ = c ^ 0100; - } else { - *q++ = c; + FD_SET (conn, &readfds); } - p++; - } - *q = '\0'; + else { +#define BUFSIZE 1024 + 1 + char buf[BUFSIZE]; + char *q, *p; + int n_read; - /* Now log it */ - logMessage(pri, line); + n_read = read (fd, buf, BUFSIZE); + + if (n_read < 0) { + perror ("read error"); + goto close_fd; + } + else if (n_read > 0) { + char line[BUFSIZE]; + unsigned char c; + int pri = (LOG_USER | LOG_NOTICE); + + memset (line, 0, sizeof(line)); + p = buf; + q = line; + while (p && (c = *p) && q < &line[sizeof(line) - 1]) { + if (c == '<') { + /* Parse the magic priority number */ + pri = 0; + while (isdigit(*(++p))) { + pri = 10 * pri + (*p - '0'); + } + if (pri & ~(LOG_FACMASK | LOG_PRIMASK)) + pri = (LOG_USER | LOG_NOTICE); + } else if (c == '\n') { + *q++ = ' '; + } else if (iscntrl(c) && (c < 0177)) { + *q++ = '^'; + *q++ = c ^ 0100; + } else { + *q++ = c; + } + p++; + } + *q = '\0'; + + /* Now log it */ + logMessage(pri, line); + + close_fd: + close (fd); + FD_CLR (fd, &readfds); + } + else { /* EOF */ + goto close_fd; + } + } + } } - close(conn); } - - close(fd); } #ifdef BB_KLOGD @@ -251,7 +298,8 @@ static void klogd_signal(int sig) exit(TRUE); } -static void doKlogd(void) +static void doKlogd (void) __attribute__ ((noreturn)); +static void doKlogd (void) { int priority = LOG_INFO; char log_buffer[4096]; @@ -317,6 +365,16 @@ static void doKlogd(void) #endif +static void daemon_init (char **argv, char *dz, void fn (void)) __attribute__ ((noreturn)); +static void daemon_init (char **argv, char *dz, void fn (void)) +{ + setsid(); + chdir ("/"); + strncpy(argv[0], dz, strlen(argv[0])); + fn(); + exit(0); +} + extern int syslogd_main(int argc, char **argv) { int pid, klogd_pid; @@ -366,13 +424,14 @@ extern int syslogd_main(int argc, char **argv) *p++ = '\0'; } + umask(0); + #ifdef BB_KLOGD /* Start up the klogd process */ if (startKlogd == TRUE) { klogd_pid = fork(); if (klogd_pid == 0) { - strncpy(argv[0], "klogd", strlen(argv[0])); - doKlogd(); + daemon_init (argv, "klogd", doKlogd); } } #endif @@ -382,8 +441,7 @@ extern int syslogd_main(int argc, char **argv) if (pid < 0) exit(pid); else if (pid == 0) { - strncpy(argv[0], "syslogd", strlen(argv[0])); - doSyslogd(); + daemon_init (argv, "syslogd", doSyslogd); } } else { doSyslogd(); @@ -391,3 +449,11 @@ extern int syslogd_main(int argc, char **argv) exit(TRUE); } + +/* + * Local Variables + * c-file-style: "linux" + * c-basic-offset: 4 + * tab-width: 4 + * End: + */ diff --git a/umount.c b/umount.c index 23973fc85..3f84aa296 100644 --- a/umount.c +++ b/umount.c @@ -260,6 +260,8 @@ extern int umount_main(int argc, char **argv) doRemount = TRUE; break; #endif + case 'v': + break; /* ignore -v */ default: usage(umount_usage); } diff --git a/util-linux/mount.c b/util-linux/mount.c index 30a060fc1..329c07780 100644 --- a/util-linux/mount.c +++ b/util-linux/mount.c @@ -418,6 +418,7 @@ extern int mount_main(int argc, char **argv) break; #endif case 'v': + break; /* ignore -v */ case 'h': case '-': goto goodbye; diff --git a/util-linux/umount.c b/util-linux/umount.c index 23973fc85..3f84aa296 100644 --- a/util-linux/umount.c +++ b/util-linux/umount.c @@ -260,6 +260,8 @@ extern int umount_main(int argc, char **argv) doRemount = TRUE; break; #endif + case 'v': + break; /* ignore -v */ default: usage(umount_usage); } -- cgit v1.2.3