diff options
author | Denis Vlasenko <vda.linux@googlemail.com> | 2006-10-03 15:57:40 +0000 |
---|---|---|
committer | Denis Vlasenko <vda.linux@googlemail.com> | 2006-10-03 15:57:40 +0000 |
commit | fe54458e46eef445da32862b2171392be8f01ab4 (patch) | |
tree | f88b5ee99da5816f1628c9560cfabecb97468689 | |
parent | 7c1ed2e922e80b7a81da3e748cb975c876315bd5 (diff) | |
download | busybox-w32-fe54458e46eef445da32862b2171392be8f01ab4.tar.gz busybox-w32-fe54458e46eef445da32862b2171392be8f01ab4.tar.bz2 busybox-w32-fe54458e46eef445da32862b2171392be8f01ab4.zip |
runit/chpst: "change process state" utility
It's "nice" on steroids - can set uid/gid, mem/cpu limits etc. +3.5k
-rw-r--r-- | Config.in | 1 | ||||
-rw-r--r-- | Makefile | 3 | ||||
-rw-r--r-- | coreutils/env.c | 6 | ||||
-rw-r--r-- | include/applets.h | 5 | ||||
-rw-r--r-- | include/libbb.h | 7 | ||||
-rw-r--r-- | include/usage.h | 64 | ||||
-rw-r--r-- | libbb/setup_environment.c | 47 | ||||
-rw-r--r-- | libbb/xfuncs.c | 8 |
8 files changed, 107 insertions, 34 deletions
@@ -470,3 +470,4 @@ source networking/Config.in | |||
470 | source procps/Config.in | 470 | source procps/Config.in |
471 | source shell/Config.in | 471 | source shell/Config.in |
472 | source sysklogd/Config.in | 472 | source sysklogd/Config.in |
473 | source runit/Config.in | ||
@@ -34,7 +34,8 @@ vpath %/Config.in $(srctree) | |||
34 | DIRS:=applets archival archival/libunarchive coreutils console-tools \ | 34 | DIRS:=applets archival archival/libunarchive coreutils console-tools \ |
35 | debianutils editors findutils init miscutils modutils networking \ | 35 | debianutils editors findutils init miscutils modutils networking \ |
36 | networking/libiproute networking/udhcp procps loginutils shell \ | 36 | networking/libiproute networking/udhcp procps loginutils shell \ |
37 | sysklogd util-linux e2fsprogs libpwdgrp coreutils/libcoreutils libbb | 37 | sysklogd util-linux e2fsprogs libpwdgrp coreutils/libcoreutils \ |
38 | runit libbb | ||
38 | 39 | ||
39 | SRC_DIRS:=$(patsubst %,$(top_srcdir)/%,$(DIRS)) | 40 | SRC_DIRS:=$(patsubst %,$(top_srcdir)/%,$(DIRS)) |
40 | 41 | ||
diff --git a/coreutils/env.c b/coreutils/env.c index 4cdbeae6a..b42d90435 100644 --- a/coreutils/env.c +++ b/coreutils/env.c | |||
@@ -63,10 +63,10 @@ int env_main(int argc, char** argv) | |||
63 | ++argv; | 63 | ++argv; |
64 | } | 64 | } |
65 | 65 | ||
66 | if(opt & 1) | 66 | if (opt & 1) |
67 | environ = cleanenv; | 67 | environ = cleanenv; |
68 | else if(opt & 2) { | 68 | else if (opt & 2) { |
69 | while(unset_env) { | 69 | while (unset_env) { |
70 | unsetenv(unset_env->data); | 70 | unsetenv(unset_env->data); |
71 | unset_env = unset_env->link; | 71 | unset_env = unset_env->link; |
72 | } | 72 | } |
diff --git a/include/applets.h b/include/applets.h index e12f6027c..328848478 100644 --- a/include/applets.h +++ b/include/applets.h | |||
@@ -70,6 +70,7 @@ USE_CHATTR(APPLET(chattr, _BB_DIR_BIN, _BB_SUID_NEVER)) | |||
70 | USE_CHGRP(APPLET(chgrp, _BB_DIR_BIN, _BB_SUID_NEVER)) | 70 | USE_CHGRP(APPLET(chgrp, _BB_DIR_BIN, _BB_SUID_NEVER)) |
71 | USE_CHMOD(APPLET(chmod, _BB_DIR_BIN, _BB_SUID_NEVER)) | 71 | USE_CHMOD(APPLET(chmod, _BB_DIR_BIN, _BB_SUID_NEVER)) |
72 | USE_CHOWN(APPLET(chown, _BB_DIR_BIN, _BB_SUID_NEVER)) | 72 | USE_CHOWN(APPLET(chown, _BB_DIR_BIN, _BB_SUID_NEVER)) |
73 | USE_CHPST(APPLET(chpst, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | ||
73 | USE_CHROOT(APPLET(chroot, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) | 74 | USE_CHROOT(APPLET(chroot, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) |
74 | USE_CHVT(APPLET(chvt, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 75 | USE_CHVT(APPLET(chvt, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
75 | USE_CKSUM(APPLET(cksum, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 76 | USE_CKSUM(APPLET(cksum, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
@@ -106,6 +107,8 @@ USE_ED(APPLET(ed, _BB_DIR_BIN, _BB_SUID_NEVER)) | |||
106 | USE_FEATURE_GREP_EGREP_ALIAS(APPLET_NOUSAGE(egrep, grep, _BB_DIR_BIN, _BB_SUID_NEVER)) | 107 | USE_FEATURE_GREP_EGREP_ALIAS(APPLET_NOUSAGE(egrep, grep, _BB_DIR_BIN, _BB_SUID_NEVER)) |
107 | USE_EJECT(APPLET(eject, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 108 | USE_EJECT(APPLET(eject, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
108 | USE_ENV(APPLET(env, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 109 | USE_ENV(APPLET(env, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
110 | USE_ENVDIR(APPLET_ODDNAME(envdir, chpst, _BB_DIR_USR_BIN, _BB_SUID_NEVER, envdir)) | ||
111 | USE_ENVUIDGID(APPLET_ODDNAME(envuidgid, chpst, _BB_DIR_USR_BIN, _BB_SUID_NEVER, envuidgid)) | ||
109 | USE_ETHER_WAKE(APPLET_ODDNAME(ether-wake, ether_wake, _BB_DIR_USR_BIN, _BB_SUID_NEVER, ether_wake)) | 112 | USE_ETHER_WAKE(APPLET_ODDNAME(ether-wake, ether_wake, _BB_DIR_USR_BIN, _BB_SUID_NEVER, ether_wake)) |
110 | USE_EXPR(APPLET(expr, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 113 | USE_EXPR(APPLET(expr, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
111 | USE_FAKEIDENTD(APPLET(fakeidentd, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) | 114 | USE_FAKEIDENTD(APPLET(fakeidentd, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) |
@@ -244,12 +247,14 @@ USE_SETCONSOLE(APPLET(setconsole, _BB_DIR_SBIN, _BB_SUID_NEVER)) | |||
244 | USE_SETKEYCODES(APPLET(setkeycodes, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 247 | USE_SETKEYCODES(APPLET(setkeycodes, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
245 | USE_SETLOGCONS(APPLET(setlogcons, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) | 248 | USE_SETLOGCONS(APPLET(setlogcons, _BB_DIR_USR_SBIN, _BB_SUID_NEVER)) |
246 | USE_SETSID(APPLET(setsid, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 249 | USE_SETSID(APPLET(setsid, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
250 | USE_SETUIDGID(APPLET_ODDNAME(setuidgid, chpst, _BB_DIR_USR_BIN, _BB_SUID_NEVER, setuidgid)) | ||
247 | USE_FEATURE_SH_IS_ASH(APPLET_NOUSAGE(sh, ash, _BB_DIR_BIN, _BB_SUID_NEVER)) | 251 | USE_FEATURE_SH_IS_ASH(APPLET_NOUSAGE(sh, ash, _BB_DIR_BIN, _BB_SUID_NEVER)) |
248 | USE_FEATURE_SH_IS_HUSH(APPLET_NOUSAGE(sh, hush, _BB_DIR_BIN, _BB_SUID_NEVER)) | 252 | USE_FEATURE_SH_IS_HUSH(APPLET_NOUSAGE(sh, hush, _BB_DIR_BIN, _BB_SUID_NEVER)) |
249 | USE_FEATURE_SH_IS_LASH(APPLET_NOUSAGE(sh, lash, _BB_DIR_BIN, _BB_SUID_NEVER)) | 253 | USE_FEATURE_SH_IS_LASH(APPLET_NOUSAGE(sh, lash, _BB_DIR_BIN, _BB_SUID_NEVER)) |
250 | USE_FEATURE_SH_IS_MSH(APPLET_NOUSAGE(sh, msh, _BB_DIR_BIN, _BB_SUID_NEVER)) | 254 | USE_FEATURE_SH_IS_MSH(APPLET_NOUSAGE(sh, msh, _BB_DIR_BIN, _BB_SUID_NEVER)) |
251 | USE_SHA1SUM(APPLET_ODDNAME(sha1sum, md5_sha1_sum, _BB_DIR_USR_BIN, _BB_SUID_NEVER, sha1sum)) | 255 | USE_SHA1SUM(APPLET_ODDNAME(sha1sum, md5_sha1_sum, _BB_DIR_USR_BIN, _BB_SUID_NEVER, sha1sum)) |
252 | USE_SLEEP(APPLET(sleep, _BB_DIR_BIN, _BB_SUID_NEVER)) | 256 | USE_SLEEP(APPLET(sleep, _BB_DIR_BIN, _BB_SUID_NEVER)) |
257 | USE_SOFTLIMIT(APPLET_ODDNAME(softlimit, chpst, _BB_DIR_USR_BIN, _BB_SUID_NEVER, softlimit)) | ||
253 | USE_SORT(APPLET(sort, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) | 258 | USE_SORT(APPLET(sort, _BB_DIR_USR_BIN, _BB_SUID_NEVER)) |
254 | USE_START_STOP_DAEMON(APPLET_ODDNAME(start-stop-daemon, start_stop_daemon, _BB_DIR_SBIN, _BB_SUID_NEVER, start_stop_daemon)) | 259 | USE_START_STOP_DAEMON(APPLET_ODDNAME(start-stop-daemon, start_stop_daemon, _BB_DIR_SBIN, _BB_SUID_NEVER, start_stop_daemon)) |
255 | USE_STAT(APPLET(stat, _BB_DIR_BIN, _BB_SUID_NEVER)) | 260 | USE_STAT(APPLET(stat, _BB_DIR_BIN, _BB_SUID_NEVER)) |
diff --git a/include/libbb.h b/include/libbb.h index b4516e99a..222b4acec 100644 --- a/include/libbb.h +++ b/include/libbb.h | |||
@@ -488,12 +488,13 @@ extern void renew_current_security_context(void); | |||
488 | extern void set_current_security_context(security_context_t sid); | 488 | extern void set_current_security_context(security_context_t sid); |
489 | #endif | 489 | #endif |
490 | extern int run_parts(char **args, const unsigned char test_mode, char **env); | 490 | extern int run_parts(char **args, const unsigned char test_mode, char **env); |
491 | extern int restricted_shell ( const char *shell ); | 491 | extern int restricted_shell(const char *shell); |
492 | extern void setup_environment ( const char *shell, int loginshell, int changeenv, const struct passwd *pw ); | 492 | extern void setup_environment(const char *shell, int loginshell, int changeenv, const struct passwd *pw); |
493 | extern int correct_password ( const struct passwd *pw ); | 493 | extern int correct_password(const struct passwd *pw); |
494 | extern char *pw_encrypt(const char *clear, const char *salt); | 494 | extern char *pw_encrypt(const char *clear, const char *salt); |
495 | extern int obscure(const char *old, const char *newval, const struct passwd *pwdp); | 495 | extern int obscure(const char *old, const char *newval, const struct passwd *pwdp); |
496 | 496 | ||
497 | extern void xsetenv(const char *key, const char *value); | ||
497 | extern int xopen(const char *pathname, int flags); | 498 | extern int xopen(const char *pathname, int flags); |
498 | extern int xopen3(const char *pathname, int flags, int mode); | 499 | extern int xopen3(const char *pathname, int flags, int mode); |
499 | extern void xread(int fd, void *buf, size_t count); | 500 | extern void xread(int fd, void *buf, size_t count); |
diff --git a/include/usage.h b/include/usage.h index 40676c113..34b0566cd 100644 --- a/include/usage.h +++ b/include/usage.h | |||
@@ -215,6 +215,70 @@ | |||
215 | "ls -l /tmp/foo\n" \ | 215 | "ls -l /tmp/foo\n" \ |
216 | "-r--r--r-- 1 root root 0 Apr 12 18:25 /tmp/foo\n" | 216 | "-r--r--r-- 1 root root 0 Apr 12 18:25 /tmp/foo\n" |
217 | 217 | ||
218 | #define chpst_trivial_usage \ | ||
219 | "[-vP012] [-u user[:group]] [-U user[:group]] [-e dir] " \ | ||
220 | "[-/ dir] [-n nice] [-m bytes] [-d bytes] [-o files] " \ | ||
221 | "[-p processes] [-f bytes] [-c bytes] prog args" | ||
222 | #define chpst_full_usage \ | ||
223 | "Change the process state and run specified program.\n\n" \ | ||
224 | "-u user[:grp] set uid and gid\n" \ | ||
225 | "-U user[:grp] set environment variables UID and GID\n" \ | ||
226 | "-e dir set environment variables as specified by files\n" \ | ||
227 | " in the directory: file=1st_line_of_file\n" \ | ||
228 | "-/ dir chroot to dir\n" \ | ||
229 | "-n inc add inc to nice value\n" \ | ||
230 | "-m bytes limit data segment, stack segment, locked physical pages,\n" \ | ||
231 | " and total of all segment per process to bytes bytes each\n" \ | ||
232 | "-d bytes limit data segment\n" \ | ||
233 | "-o n limit the number of open file descriptors per process to n\n" \ | ||
234 | "-p n limit number of processes per uid to n\n" \ | ||
235 | "-f bytes limit output file size to bytes bytes\n" \ | ||
236 | "-c bytes limit core file size to bytes bytes\n" \ | ||
237 | "-v verbose\n" \ | ||
238 | "-P run prog in a new process group\n" \ | ||
239 | "-0 close standard input\n" \ | ||
240 | "-1 close standard output\n" \ | ||
241 | "-2 close standard error" | ||
242 | #define setuidgid_trivial_usage \ | ||
243 | "account prog args" | ||
244 | #define setuidgid_full_usage \ | ||
245 | "Sets uid and gid to account's uid and gid, removing all supplementary\n" \ | ||
246 | "groups, then runs prog" | ||
247 | #define envuidgid_trivial_usage \ | ||
248 | "account prog args" | ||
249 | #define envuidgid_full_usage \ | ||
250 | "Sets $UID to account's uid and $GID to account's gid, then runs prog" | ||
251 | #define envdir_trivial_usage \ | ||
252 | "dir prog args" | ||
253 | #define envdir_full_usage \ | ||
254 | "Sets various environment variables as specified by files\n" \ | ||
255 | "in the directory dir, then runs prog" | ||
256 | #define softlimit_trivial_usage \ | ||
257 | "[-a allbytes] [-c corebytes] [-d databytes] [-f filebytes] " \ | ||
258 | "[-l lockbytes] [-m membytes] [-o openfiles] [-p processes] " \ | ||
259 | "[-r residentbytes] [-s stackbytes] [-t cpusecs] prog args" | ||
260 | #define softlimit_full_usage \ | ||
261 | "Sets soft resource limits as specified by options, then runs prog\n" \ | ||
262 | "\n" \ | ||
263 | "-m n Same as -d n -s n -l n -a n\n" \ | ||
264 | "-d n Limit the data segment per process to n bytes\n" \ | ||
265 | "-s n Limit the stack segment per process to n bytes\n" \ | ||
266 | "-l n Limit the locked physical pages per process to n bytes\n" \ | ||
267 | "-a n Limit the total of all segments per process to n bytes\n" \ | ||
268 | "-o n Limit the number of open file descriptors per process to n\n" \ | ||
269 | "-p n Limit the number of processes per uid to n\n" \ | ||
270 | "Options controlling file sizes:\n" \ | ||
271 | "-f n Limit output file sizes to n bytes\n" \ | ||
272 | "-c n Limit core file sizes to n bytes\n" \ | ||
273 | "Efficiency opts:\n" \ | ||
274 | "-r n Limit the resident set size to n bytes. This limit is not\n" \ | ||
275 | " enforced unless physical memory is full\n" \ | ||
276 | "-t n Limit the CPU time to n seconds. This limit is not enforced\n" \ | ||
277 | " except that the process receives a SIGXCPU signal after n seconds\n" \ | ||
278 | "\n" \ | ||
279 | "Some options may have no effect on some operating systems\n" \ | ||
280 | "n may be =, indicating that soft limit should be set equal to hard limit" | ||
281 | |||
218 | #define chroot_trivial_usage \ | 282 | #define chroot_trivial_usage \ |
219 | "NEWROOT [COMMAND...]" | 283 | "NEWROOT [COMMAND...]" |
220 | #define chroot_full_usage \ | 284 | #define chroot_full_usage \ |
diff --git a/libbb/setup_environment.c b/libbb/setup_environment.c index a14649625..874a58efa 100644 --- a/libbb/setup_environment.c +++ b/libbb/setup_environment.c | |||
@@ -42,15 +42,9 @@ | |||
42 | #define DEFAULT_LOGIN_PATH "/bin:/usr/bin" | 42 | #define DEFAULT_LOGIN_PATH "/bin:/usr/bin" |
43 | #define DEFAULT_ROOT_LOGIN_PATH "/usr/sbin:/bin:/usr/bin:/sbin" | 43 | #define DEFAULT_ROOT_LOGIN_PATH "/usr/sbin:/bin:/usr/bin:/sbin" |
44 | 44 | ||
45 | static void xsetenv ( const char *key, const char *value ) | 45 | void setup_environment(const char *shell, int loginshell, int changeenv, const struct passwd *pw) |
46 | { | 46 | { |
47 | if ( setenv ( key, value, 1 )) | 47 | if (loginshell) { |
48 | bb_error_msg_and_die (bb_msg_memory_exhausted); | ||
49 | } | ||
50 | |||
51 | void setup_environment ( const char *shell, int loginshell, int changeenv, const struct passwd *pw ) | ||
52 | { | ||
53 | if ( loginshell ) { | ||
54 | const char *term; | 48 | const char *term; |
55 | 49 | ||
56 | /* Change the current working directory to be the home directory | 50 | /* Change the current working directory to be the home directory |
@@ -59,32 +53,31 @@ void setup_environment ( const char *shell, int loginshell, int changeenv, const | |||
59 | * directory. | 53 | * directory. |
60 | * Some systems default to HOME=/ | 54 | * Some systems default to HOME=/ |
61 | */ | 55 | */ |
62 | if ( chdir ( pw-> pw_dir )) { | 56 | if (chdir(pw->pw_dir)) { |
63 | xchdir ( "/" ); | 57 | xchdir("/"); |
64 | fputs ( "warning: cannot change to home directory\n", stderr ); | 58 | fputs("warning: cannot change to home directory\n", stderr); |
65 | } | 59 | } |
66 | 60 | ||
67 | /* Leave TERM unchanged. Set HOME, SHELL, USER, LOGNAME, PATH. | 61 | /* Leave TERM unchanged. Set HOME, SHELL, USER, LOGNAME, PATH. |
68 | Unset all other environment variables. */ | 62 | Unset all other environment variables. */ |
69 | term = getenv ("TERM"); | 63 | term = getenv("TERM"); |
70 | clearenv ( ); | 64 | clearenv(); |
71 | if ( term ) | 65 | if (term) |
72 | xsetenv ( "TERM", term ); | 66 | xsetenv("TERM", term); |
73 | xsetenv ( "HOME", pw-> pw_dir ); | 67 | xsetenv("HOME", pw->pw_dir); |
74 | xsetenv ( "SHELL", shell ); | 68 | xsetenv("SHELL", shell); |
75 | xsetenv ( "USER", pw-> pw_name ); | 69 | xsetenv("USER", pw->pw_name); |
76 | xsetenv ( "LOGNAME", pw-> pw_name ); | 70 | xsetenv("LOGNAME", pw->pw_name); |
77 | xsetenv ( "PATH", ( pw-> pw_uid ? DEFAULT_LOGIN_PATH : DEFAULT_ROOT_LOGIN_PATH )); | 71 | xsetenv("PATH", (pw->pw_uid ? DEFAULT_LOGIN_PATH : DEFAULT_ROOT_LOGIN_PATH)); |
78 | } | 72 | } |
79 | else if ( changeenv ) { | 73 | else if (changeenv) { |
80 | /* Set HOME, SHELL, and if not becoming a super-user, | 74 | /* Set HOME, SHELL, and if not becoming a super-user, |
81 | USER and LOGNAME. */ | 75 | USER and LOGNAME. */ |
82 | xsetenv ( "HOME", pw-> pw_dir ); | 76 | xsetenv("HOME", pw->pw_dir); |
83 | xsetenv ( "SHELL", shell ); | 77 | xsetenv("SHELL", shell); |
84 | if ( pw-> pw_uid ) { | 78 | if (pw->pw_uid) { |
85 | xsetenv ( "USER", pw-> pw_name ); | 79 | xsetenv("USER", pw->pw_name); |
86 | xsetenv ( "LOGNAME", pw-> pw_name ); | 80 | xsetenv("LOGNAME", pw->pw_name); |
87 | } | 81 | } |
88 | } | 82 | } |
89 | } | 83 | } |
90 | |||
diff --git a/libbb/xfuncs.c b/libbb/xfuncs.c index 92091e555..7b95e49f1 100644 --- a/libbb/xfuncs.c +++ b/libbb/xfuncs.c | |||
@@ -255,6 +255,14 @@ int wait4pid(int pid) | |||
255 | } | 255 | } |
256 | #endif | 256 | #endif |
257 | 257 | ||
258 | #ifdef L_xsetenv | ||
259 | void xsetenv(const char *key, const char *value) | ||
260 | { | ||
261 | if(setenv(key, value, 1)) | ||
262 | bb_error_msg_and_die(bb_msg_memory_exhausted); | ||
263 | } | ||
264 | #endif | ||
265 | |||
258 | #ifdef L_itoa | 266 | #ifdef L_itoa |
259 | // Convert unsigned integer to ascii, writing into supplied buffer. A | 267 | // Convert unsigned integer to ascii, writing into supplied buffer. A |
260 | // truncated result is always null terminated (unless buflen is 0), and | 268 | // truncated result is always null terminated (unless buflen is 0), and |