httpd-cvs mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From j..@apache.org
Subject svn commit: r543511 - /httpd/httpd/branches/1.3.x/src/main/http_main.c
Date Fri, 01 Jun 2007 15:42:58 GMT
Author: jim
Date: Fri Jun  1 08:42:57 2007
New Revision: 543511

URL: http://svn.apache.org/viewvc?view=rev&rev=543511
Log:
Add in parent process PID table, to provide for
a check against the pid values located in the
scoreboard.

Modified:
    httpd/httpd/branches/1.3.x/src/main/http_main.c

Modified: httpd/httpd/branches/1.3.x/src/main/http_main.c
URL: http://svn.apache.org/viewvc/httpd/httpd/branches/1.3.x/src/main/http_main.c?view=diff&rev=543511&r1=543510&r2=543511
==============================================================================
--- httpd/httpd/branches/1.3.x/src/main/http_main.c (original)
+++ httpd/httpd/branches/1.3.x/src/main/http_main.c Fri Jun  1 08:42:57 2007
@@ -354,9 +354,17 @@
 char tpf_mutex_key[TPF_MUTEX_KEY_SIZE];
 #endif /* TPF */
 
+/*
+ * Shared memory scoreboard
+ */
 scoreboard *ap_scoreboard_image = NULL;
 
 /*
+ * Parent process local storage of child pids
+ */
+static table *pid_table;
+
+/*
  * Pieces for managing the contents of the Server response header
  * field.
  */
@@ -372,6 +380,32 @@
 API_VAR_EXPORT int ap_change_shmem_uid = 0;
 
 /*
+ * Check the pid table to see if the actual pid exists
+ */
+static int in_pid_table(int pid) {
+    char apid[64];
+    const char *spid;
+    snprintf(apid, sizeof(apid), "%d", pid);
+    spid = ap_table_get(pid_table, apid);
+    if (spid && spid[0] == '1' && spid[1] == '\0')
+        return 1;
+    else
+        return 0;
+}
+
+static void set_pid_table(int pid) {
+    char apid[64];
+    snprintf(apid, sizeof(apid), "%d", pid);
+    ap_table_set(pid_table, apid, "1");
+}
+
+static void unset_pid_table(int pid) {
+    char apid[64];
+    snprintf(apid, sizeof(apid), "%d", pid);
+    ap_table_unset(pid_table, apid);
+}
+
+/*
  * This routine is called when the pconf pool is vacuumed.  It resets the
  * server version string to a known value and [re]enables modifications
  * (which are disabled by configuration completion). 
@@ -2787,6 +2821,11 @@
 	    if (pid == my_pid || pid == 0)
 		continue;
 
+            if (!in_pid_table(pid)) {
+                ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, server_conf,
+                             "Bad pid (%d) in scoreboard slot %d", pid, i);
+                continue;
+            }
 	    waitret = waitpid(pid, &status, WNOHANG);
 	    if (waitret == pid || waitret == -1) {
 		ap_scoreboard_image->parent[i].pid = 0;
@@ -2887,13 +2926,22 @@
 
     for (n = 0; n < max_daemons_limit; ++n) {
         ap_sync_scoreboard_image();
-	if (ap_scoreboard_image->servers[n].status != SERVER_DEAD &&
-		kill((pid = ap_scoreboard_image->parent[n].pid), 0) == -1) {
-	    ap_update_child_status(n, SERVER_DEAD, NULL);
-	    /* just mark it as having a successful exit status */
-	    bzero((char *) status, sizeof(ap_wait_t));
-	    return(pid);
-	}
+        pid = ap_scoreboard_image->parent[n].pid;
+        if (ap_scoreboard_image->servers[n].status != SERVER_DEAD) {
+            if (in_pid_table(pid)) {
+                if (kill(pid, 0) == -1) {
+                    ap_update_child_status(n, SERVER_DEAD, NULL);
+                    /* just mark it as having a successful exit status */
+                    bzero((char *) status, sizeof(ap_wait_t));
+                    unset_pid_table(pid);
+                    return(pid);
+                }
+            }
+            else {
+                ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, server_conf,
+                            "Bad pid (%d) in scoreboard slot %d", pid, n);
+            }
+        }
     }
     return 0;
 }
@@ -2916,15 +2964,21 @@
 #define MAXWAITOBJ MAXIMUM_WAIT_OBJECTS
     HANDLE h[MAXWAITOBJ];
     int e[MAXWAITOBJ];
-    int round, pi, hi, rv, err;
+    int round, pi, hi, rv, err, pid;
     for (round = 0; round <= (HARD_SERVER_LIMIT - 1) / MAXWAITOBJ + 1; round++) {
 	hi = 0;
 	for (pi = round * MAXWAITOBJ;
 	     (pi < (round + 1) * MAXWAITOBJ) && (pi < HARD_SERVER_LIMIT);
 	     pi++) {
 	    if (ap_scoreboard_image->servers[pi].status != SERVER_DEAD) {
-		e[hi] = pi;
-		h[hi++] = (HANDLE) ap_scoreboard_image->parent[pi].pid;
+                e[hi] = pi;
+                pid = ap_scoreboard_image->parent[pi].pid;
+                if (in_pid_table(pid))
+                    h[hi++] = (HANDLE) pid;
+                else {
+                    ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, server_conf,
+                                 "Bad pid (%d) in scoreboard slot %d", pid, pi);
+                }
 	    }
 
 	}
@@ -4339,6 +4393,7 @@
     ap_server_pre_read_config  = ap_make_array(pcommands, 1, sizeof(char *));
     ap_server_post_read_config = ap_make_array(pcommands, 1, sizeof(char *));
     ap_server_config_defines   = ap_make_array(pcommands, 1, sizeof(char *));
+    pid_table                  = ap_make_table(pglobal, HARD_SERVER_LIMIT);
 }
 
 #ifndef MULTITHREAD
@@ -4987,6 +5042,7 @@
     ap_scoreboard_image->parent[slot].last_rtime = now;
 #endif
     ap_scoreboard_image->parent[slot].pid = pid;
+    set_pid_table(pid);
 #ifdef SCOREBOARD_FILE
     lseek(scoreboard_fd, XtOffsetOf(scoreboard, parent[slot]), 0);
     force_write(scoreboard_fd, &ap_scoreboard_image->parent[slot],
@@ -5049,6 +5105,7 @@
     int i;
     int to_kill;
     int idle_count;
+    int pid;
     short_score *ss;
     time_t now = time(NULL);
     int free_length;
@@ -5113,8 +5170,15 @@
 		else if (ps->last_rtime + ss->timeout_len < now) {
 		    /* no progress, and the timeout length has been exceeded */
 		    ss->timeout_len = 0;
-		    kill(ps->pid, SIG_TIMEOUT_KILL);
-		}
+                    pid = ps->pid;
+                    if (in_pid_table(pid)) {
+                        kill(pid, SIG_TIMEOUT_KILL);
+                    }
+                    else {
+                        ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, server_conf,
+                            "Bad pid (%d) in scoreboard slot %d", pid, i);
+                    }
+                }
 	    }
 #endif
 	}
@@ -5126,11 +5190,19 @@
 	 * while we were counting. Use the define SIG_IDLE_KILL to reflect
 	 * which signal should be used on the specific OS.
 	 */
-	kill(ap_scoreboard_image->parent[to_kill].pid, SIG_IDLE_KILL);
-	idle_spawn_rate = 1;
+        pid = ap_scoreboard_image->parent[to_kill].pid;
+        if (in_pid_table(pid)) {
+            kill(pid, SIG_IDLE_KILL);
+            idle_spawn_rate = 1;
 #ifdef TPF
-        ap_update_child_status(to_kill, SERVER_DEAD, (request_rec *)NULL);
+            ap_update_child_status(to_kill, SERVER_DEAD, (request_rec *)NULL);
 #endif
+            unset_pid_table(pid);
+        }
+        else {
+            ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, server_conf,
+                         "Bad pid (%d) in scoreboard slot %d", pid, to_kill);
+        }
     }
     else if (idle_count < ap_daemons_min_free) {
 	/* terminate the free list */
@@ -5385,6 +5457,7 @@
 		if (child_slot >= 0) {
 		    (void) ap_update_child_status(child_slot, SERVER_DEAD,
 					       (request_rec *) NULL);
+		    unset_pid_table(pid);
 		    if (remaining_children_to_start
 			&& child_slot < ap_daemons_limit) {
 			/* we're still doing a 1-for-1 replacement of dead



Mime
View raw message