diff options
author | Ryan Bloom <rbb@apache.org> | 2000-06-06 21:45:11 +0000 |
---|---|---|
committer | Ryan Bloom <rbb@apache.org> | 2000-06-06 21:45:11 +0000 |
commit | 7de6d7e9862ad9919616ecbccc5427c1efd83f18 (patch) | |
tree | 0058673381a07ed45e735a3eeb4775c038e26e73 /threadproc/unix/proc.c | |
parent | af4e91e5c49ee29a0ea5bc0bab1d61ee1230f800 (diff) | |
download | apr-7de6d7e9862ad9919616ecbccc5427c1efd83f18.tar.gz apr-7de6d7e9862ad9919616ecbccc5427c1efd83f18.zip |
Add the resource limiting code back to Apache 2.0. This only works on
Unix because I can't find any other platforms with rlimit. If there are
other platforms that need this code, then some of the code needs to move.
This has just barely been tested, so it could probably use some good
testing.
git-svn-id: https://svn.apache.org/repos/asf/apr/apr/trunk@60147 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'threadproc/unix/proc.c')
-rw-r--r-- | threadproc/unix/proc.c | 75 |
1 files changed, 75 insertions, 0 deletions
diff --git a/threadproc/unix/proc.c b/threadproc/unix/proc.c index 9175585a3..c74fdc0d6 100644 --- a/threadproc/unix/proc.c +++ b/threadproc/unix/proc.c @@ -212,6 +212,48 @@ ap_status_t ap_fork(ap_proc_t *proc, ap_pool_t *cont) return APR_INPARENT; } +#if APR_HAVE_STRUCT_RLIMIT +#if defined(RLIMIT_CPU) || defined(RLIMIT_NPROC) || defined(RLIMIT_AS) || defined(RLIMIT_DATA) || defined(RLIMIT_VMEM) +static ap_status_t limit_proc(ap_procattr_t *attr) +{ +#ifdef RLIMIT_CPU + if (attr->limit_cpu != NULL) { + if ((setrlimit(RLIMIT_CPU, attr->limit_cpu)) != 0) { + return errno; + } + } +#endif +#ifdef RLIMIT_NPROC + if (attr->limit_nproc != NULL) { + if ((setrlimit(RLIMIT_NPROC, attr->limit_nproc)) != 0) { + return errno; + } + } +#endif +#if defined(RLIMIT_AS) + if (attr->limit_mem != NULL) { + if ((setrlimit(RLIMIT_AS, attr->limit_mem)) != 0) { + return errno; + } + } +#elif defined(RLIMIT_DATA) + if (attr->limit_mem != NULL) { + if ((setrlimit(RLIMIT_DATA, attr->limit_mem)) != 0) { + return errno; + } + } +#elif defined(RLIMIT_VMEM) + if (attr->limit_mem != NULL) { + if ((setrlimit(RLIMIT_VMEM, attr->limit_mem)) != 0) { + return errno; + } + } +#endif + return APR_SUCCESS; +} +#endif +#endif + ap_status_t ap_create_process(ap_proc_t *new, const char *progname, char *const args[], char **env, ap_procattr_t *attr, ap_pool_t *cont) @@ -228,6 +270,7 @@ ap_status_t ap_create_process(ap_proc_t *new, const char *progname, return errno; } else if (new->pid == 0) { + int status; /* child process */ if (attr->child_in) { ap_close(attr->parent_in); @@ -255,6 +298,12 @@ ap_status_t ap_create_process(ap_proc_t *new, const char *progname, ap_cleanup_for_exec(); +#if defined(RLIMIT_CPU) || defined(RLIMIT_NPROC) || defined(RLIMIT_AS) || defined(RLIMIT_DATA) || defined(RLIMIT_VMEM) + if ((status = limit_proc(attr)) != APR_SUCCESS) { + return status; + } +#endif + if (attr->cmdtype == APR_SHELLCMD) { i = 0; while (args[i]) { @@ -338,3 +387,29 @@ ap_status_t ap_wait_proc(ap_proc_t *proc, } return errno; } + +ap_status_t ap_setprocattr_limit(ap_procattr_t *attr, ap_int32_t what, + struct rlimit *limit) +{ + switch(what) { + case APR_LIMIT_CPU: +#ifdef RLIMIT_CPU + attr->limit_cpu = limit; +#else + return APR_ENOTIMPL; +#endif + case APR_LIMIT_MEM: +#if defined (RLIMIT_DATA) || defined (RLIMIT_VMEM) || defined(RLIMIT_AS) + attr->limit_mem = limit; +#else + return APR_ENOTIMPL; +#endif + case APR_LIMIT_NPROC: +#ifdef RLIMIT_NPROC + attr->limit_nproc = limit; +#else + return APR_ENOTIMPL; +#endif + } + return APR_SUCCESS; +} |