prefork.c revision b7973a1e572a3ff7cdedb48ed1f9481ece700bf9
a78048ccbdb6256da15e6b0e7e95355e480c2301nd/* ====================================================================
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * The Apache Software License, Version 1.1
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * Copyright (c) 2000-2003 The Apache Software Foundation. All rights
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * reserved.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * Redistribution and use in source and binary forms, with or without
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * modification, are permitted provided that the following conditions
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * are met:
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * 1. Redistributions of source code must retain the above copyright
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * notice, this list of conditions and the following disclaimer.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * 2. Redistributions in binary form must reproduce the above copyright
27e52281f1522522b170cafc76b08b58aa70ccaand * notice, this list of conditions and the following disclaimer in
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * the documentation and/or other materials provided with the
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * distribution.
4b5981e276e93df97c34e4da05ca5cf8bbd937dand * 3. The end-user documentation included with the redistribution,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * if any, must include the following acknowledgment:
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * "This product includes software developed by the
e609c337f729875bc20e01096c7e610f45356f54nilgun * Apache Software Foundation (http://www.apache.org/)."
e609c337f729875bc20e01096c7e610f45356f54nilgun * Alternately, this acknowledgment may appear in the software itself,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * if and wherever such third-party acknowledgments normally appear.
9bcfc3697a91b5215893a7d0206865b13fc72148nd * 4. The names "Apache" and "Apache Software Foundation" must
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * not be used to endorse or promote products derived from this
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * software without prior written permission. For written
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * permission, please contact apache@apache.org.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * 5. Products derived from this software may not be called "Apache",
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * nor may "Apache" appear in their name, without prior written
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * permission of the Apache Software Foundation.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * SUCH DAMAGE.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * ====================================================================
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * This software consists of voluntary contributions made by many
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * individuals on behalf of the Apache Software Foundation. For more
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * information on the Apache Software Foundation, please see
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * Portions of this software are based upon public domain software
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * originally written at the National Center for Supercomputing Applications,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * University of Illinois, Urbana-Champaign.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd/* Limit on the total --- clients will be locked out if more servers than
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * this are needed. It is intended solely to keep the server from crashing
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * when things get out of hand.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * We keep a hard maximum number of servers, for two reasons --- first off,
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * in case something goes seriously wrong, we want to stop the fork bomb
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * short of actually crashing the machine we're running on by filling some
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * kernel table. Secondly, it keeps the size of the scoreboard file small
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * enough that we can read the whole thing without worrying too much about
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * the overhead.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd/* Admin can't tune ServerLimit beyond MAX_SERVER_LIMIT. We want
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * some sort of compile-time limit to help catch typos.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd/* config globals */
a78048ccbdb6256da15e6b0e7e95355e480c2301ndint ap_threads_per_child=0; /* Worker threads per child */
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * The max child slot ever assigned, preserved across restarts. Necessary
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * to deal with MaxClients changes across AP_SIG_GRACEFUL restarts. We
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * use this value to optimize routines that have to scan the entire scoreboard.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd/* one_process --- debugging mode variable; can be set from the command line
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * with the -X flag. If set, this gets you the child_main loop running
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * in the process which originally started up (no detach, no make_child),
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * which is a pretty nice debugging environment. (You'll get a SIGHUP
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * early in standalone_main; just continue through. This is the server
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * trying to kill off any child processes which it might have lying
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * around --- Apache doesn't keep track of their pids, it just sends
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * SIGHUP to the process group, ignoring it in the root process.
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * Continue through and you'll be fine.).
a78048ccbdb6256da15e6b0e7e95355e480c2301ndstatic int one_process = 0;
a78048ccbdb6256da15e6b0e7e95355e480c2301ndstatic apr_pool_t *pchild; /* Pool for httpd child stuff */
a78048ccbdb6256da15e6b0e7e95355e480c2301ndstatic pid_t ap_my_pid; /* it seems silly to call getpid all the time */
a78048ccbdb6256da15e6b0e7e95355e480c2301nd#endif /* TPF */
a78048ccbdb6256da15e6b0e7e95355e480c2301ndstatic int die_now = 0;
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * change directory for gprof to plop the gmon.out file
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * configure in httpd.conf:
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * GprofDir $RuntimeDir/ -> $ServerRoot/$RuntimeDir/gmon.out
a78048ccbdb6256da15e6b0e7e95355e480c2301nd * GprofDir $RuntimeDir/% -> $ServerRoot/$RuntimeDir/gprof.$pid/gmon.out
a78048ccbdb6256da15e6b0e7e95355e480c2301ndstatic void chdir_for_gprof(void)
a78048ccbdb6256da15e6b0e7e95355e480c2301nd ap_get_module_config(ap_server_conf->module_config, &core_module);
a78048ccbdb6256da15e6b0e7e95355e480c2301nd const char *use_dir;
#define chdir_for_gprof()
#define ap_check_signals()
if (pchild) {
static void accept_mutex_on(void)
if (ap_my_generation !=
clean_child_exit(0);
static void accept_mutex_off(void)
if (ap_my_generation !=
switch(query_code){
case AP_MPMQ_MAX_DAEMON_USED:
return APR_SUCCESS;
case AP_MPMQ_IS_THREADED:
return APR_SUCCESS;
case AP_MPMQ_IS_FORKED:
return APR_SUCCESS;
return APR_SUCCESS;
return APR_SUCCESS;
case AP_MPMQ_MAX_THREADS:
*result = 0;
return APR_SUCCESS;
return APR_SUCCESS;
*result = 0;
return APR_SUCCESS;
return APR_SUCCESS;
*result = 0;
return APR_SUCCESS;
return APR_SUCCESS;
case AP_MPMQ_MAX_DAEMONS:
return APR_SUCCESS;
return APR_ENOTIMPL;
#if defined(NEED_WAITPID)
int n, pid;
for (n = 0; n < ap_max_daemons_limit; ++n) {
*exitcode = 0;
return(pid);
clean_child_exit(0);
static int volatile shutdown_pending;
static int volatile restart_pending;
static int volatile is_graceful;
static void set_signals(void)
#ifndef NO_USE_SIGACTION
if (!one_process) {
#ifndef NO_USE_SIGACTION
#ifdef SIGINT
#ifdef SIGXCPU
#ifdef SIGXFSZ
#ifdef SIGPIPE
ap_log_error(APLOG_MARK, APLOG_WARNING, errno, ap_server_conf, "sigaction(" AP_SIG_GRACEFUL_STRING ")");
if (!one_process) {
#ifdef SIGXCPU
#ifdef SIGXFSZ
#ifdef SIGHUP
#ifdef AP_SIG_GRACEFUL
#ifdef SIGPIPE
static int requests_this_child;
static int num_listensocks = 0;
int ap_graceful_stop_signalled(void)
int offset;
void *csd;
requests_this_child = 0;
if (unixd_setup_child()) {
for (i = 0; i < num_listensocks; i++) {
while (!die_now) {
if ((ap_max_requests_per_child > 0
clean_child_exit(0);
offset = 0;
apr_int32_t n;
curr_pollfd++;
curr_pollfd = 0;
goto got_fd;
current_conn = ap_run_create_connection(ptrans, ap_server_conf, csd, my_child_num, sbh, bucket_alloc);
if (current_conn) {
else if (ap_my_generation !=
clean_child_exit(0);
int pid;
if (one_process) {
#ifdef SIGQUIT
#ifdef _OSD_POSIX
if (!pid) {
#ifdef HAVE_BINDPROCESSOR
#ifndef MAX_SPAWN_RATE
static int hold_off_on_exponential_spawning;
int to_kill;
int idle_count;
int free_length;
int last_non_dead;
int total_non_dead;
free_length = 0;
idle_count = 0;
total_non_dead = 0;
for (i = 0; i < ap_daemons_limit; ++i) {
int status;
++free_length;
++ idle_count;
to_kill = i;
last_non_dead = i;
if (free_length == 0) {
static int reported = 0;
if (!reported) {
"to increase StartServers, or Min/MaxSpareServers), "
for (i = 0; i < free_length; ++i) {
#ifdef TPF
int index;
if (changed_limit_at_restart) {
if (!is_graceful) {
set_signals();
if (one_process) {
if (!is_graceful) {
int child_slot;
if (child_slot >= 0) {
else if (remaining_children_to_start
else if (is_graceful) {
0, ap_server_conf,
else if (remaining_children_to_start) {
#ifdef TPF
if (shutdown_pending) {
0, ap_server_conf,
if (one_process) {
if (is_graceful) {
pconf = p;
ap_server_conf = s;
return DONE;
return DONE;
return OK;
static int restart_num = 0;
if (debug) {
no_detach = 0;
is_graceful = 0;
return HTTP_INTERNAL_SERVER_ERROR;
ap_extended_status = 0;
#ifdef AP_MPM_WANT_SET_MAX_MEM_FREE
return OK;
#ifdef AUX3
(void) set42sig();
return err;
return NULL;
return err;
if (ap_daemons_min_free <= 0) {
return NULL;
return err;
return NULL;
return err;
return NULL;
int tmp_server_limit;
return err;
if (first_server_limit &&
return NULL;
return NULL;
{ NULL }