httpd-cvs mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From gst...@apache.org
Subject cvs commit: httpd-2.0/server/mpm/prefork prefork.c
Date Sun, 16 Nov 2003 23:03:18 GMT
gstein      2003/11/16 15:03:18

  Modified:    server/mpm/prefork prefork.c
  Log:
  Switch the prefork MPM over to the new pollset interface.
  
  * server/mpm/prefork/prefork.c:
    (listensocks[]): removed. not required.
    (child_main): stop using listensocks[] in favor of an apr_pollset_t. if
      there is just one listener, then always refer to that listener's
      listen_rec for further processing, otherwise poll and pick up the
      listen_rec pointer from the polling structure's client_data. tweaked
      the round-robin for the new pollset API (and documented).
      cleaning: removed 'offset' which is obviated by the use of a pointer
        to a listen_rec. tighten the block-scope of several variables.
        switch to use a 'status' variable name rather than three separately
        named variables. rename n->numdesc to be more obvious.
  
  Revision  Changes    Path
  1.282     +56 -51    httpd-2.0/server/mpm/prefork/prefork.c
  
  Index: prefork.c
  ===================================================================
  RCS file: /home/cvs/httpd-2.0/server/mpm/prefork/prefork.c,v
  retrieving revision 1.281
  retrieving revision 1.282
  diff -u -r1.281 -r1.282
  --- prefork.c	7 Nov 2003 13:40:04 -0000	1.281
  +++ prefork.c	16 Nov 2003 23:03:18 -0000	1.282
  @@ -476,7 +476,7 @@
   
   static int requests_this_child;
   static int num_listensocks = 0;
  -static ap_listen_rec *listensocks;
  +
   
   int ap_graceful_stop_signalled(void)
   {
  @@ -489,21 +489,16 @@
   {
       apr_pool_t *ptrans;
       apr_allocator_t *allocator;
  -    conn_rec *current_conn;
  -    apr_status_t status = APR_EINIT;
  +    apr_status_t status;
       int i;
       ap_listen_rec *lr;
  -    int curr_pollfd, last_pollfd = 0;
  -    apr_pollfd_t *pollset;
  -    int offset;
  -    void *csd;
  +    apr_pollset_t *pollset;
       ap_sb_handle_t *sbh;
  -    apr_status_t rv;
       apr_bucket_alloc_t *bucket_alloc;
  +    int last_poll_idx = 0;
   
       my_child_num = child_num_arg;
       ap_my_pid = getpid();
  -    csd = NULL;
       requests_this_child = 0;
   
       ap_fatal_signal_child_setup(ap_server_conf);
  @@ -521,9 +516,9 @@
   
       /* needs to be done before we switch UIDs so we have permissions */
       ap_reopen_scoreboard(pchild, NULL, 0);
  -    rv = apr_proc_mutex_child_init(&accept_mutex, ap_lock_fname, pchild);
  -    if (rv != APR_SUCCESS) {
  -        ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,
  +    status = apr_proc_mutex_child_init(&accept_mutex, ap_lock_fname, pchild);
  +    if (status != APR_SUCCESS) {
  +        ap_log_error(APLOG_MARK, APLOG_EMERG, status, ap_server_conf,
                        "Couldn't initialize cross-process lock in child");
           clean_child_exit(APEXIT_CHILDFATAL);
       }
  @@ -539,30 +534,31 @@
       (void) ap_update_child_status(sbh, SERVER_READY, (request_rec *) NULL);
   
       /* Set up the pollfd array */
  -    listensocks = apr_pcalloc(pchild,
  -                            sizeof(*listensocks) * (num_listensocks));
  -    for (lr = ap_listeners, i = 0; i < num_listensocks; lr = lr->next, i++) {
  -        listensocks[i].accept_func = lr->accept_func;
  -        listensocks[i].sd = lr->sd;
  -    }
  +    /* ### check the status */
  +    (void) apr_pollset_create(&pollset, num_listensocks, pchild, 0);
  +
  +    for (lr = ap_listeners, i = num_listensocks; i--; lr = lr->next) {
  +        apr_pollfd_t pfd = { 0 };
   
  -    pollset = apr_palloc(pchild, sizeof(*pollset) * num_listensocks);
  -    pollset[0].p = pchild;
  -    for (i = 0; i < num_listensocks; i++) {
  -        pollset[i].desc.s = listensocks[i].sd;
  -        pollset[i].desc_type = APR_POLL_SOCKET;
  -        pollset[i].reqevents = APR_POLLIN;
  +        pfd.desc_type = APR_POLL_SOCKET;
  +        pfd.desc.s = lr->sd;
  +        pfd.reqevents = APR_POLLIN;
  +        pfd.client_data = lr;
  +
  +        /* ### check the status */
  +        (void) apr_pollset_add(pollset, &pfd);
       }
   
       bucket_alloc = apr_bucket_alloc_create(pchild);
   
       while (!die_now) {
  +        conn_rec *current_conn;
  +        void *csd;
  +
   	/*
   	 * (Re)initialize this child to a pre-connection state.
   	 */
   
  -	current_conn = NULL;
  -
   	apr_pool_clear(ptrans);
   
   	if ((ap_max_requests_per_child > 0
  @@ -580,17 +576,19 @@
   	SAFE_ACCEPT(accept_mutex_on());
   
           if (num_listensocks == 1) {
  -            offset = 0;
  +            /* There is only one listener record, so refer to that one. */
  +            lr = ap_listeners;
           }
           else {
               /* multiple listening sockets - need to poll */
   	    for (;;) {
  -                apr_status_t ret;
  -                apr_int32_t n;
  +                apr_int32_t numdesc;
  +                const apr_pollfd_t *pdesc;
   
  -                ret = apr_poll(pollset, num_listensocks, &n, -1);
  -                if (ret != APR_SUCCESS) {
  -                    if (APR_STATUS_IS_EINTR(ret)) {
  +                /* timeout == -1 == wait forever */
  +                status = apr_pollset_poll(pollset, -1, &numdesc, &pdesc);
  +                if (status != APR_SUCCESS) {
  +                    if (APR_STATUS_IS_EINTR(status)) {
                           if (one_process && shutdown_pending) {
                               return;
                           }
  @@ -602,34 +600,41 @@
       	             * on Linux 2.0.x we seem to end up with EFAULT
       	             * occasionally, and we'd loop forever due to it.
       	             */
  -    	            ap_log_error(APLOG_MARK, APLOG_ERR, ret, ap_server_conf,
  -                             "apr_poll: (listen)");
  +    	            ap_log_error(APLOG_MARK, APLOG_ERR, status,
  +                                 ap_server_conf, "apr_poll: (listen)");
       	            clean_child_exit(1);
                   }
  -                /* find a listener */
  -                curr_pollfd = last_pollfd;
  -                do {
  -                    curr_pollfd++;
  -                    if (curr_pollfd >= num_listensocks) {
  -                        curr_pollfd = 0;
  -                    }
  -                    /* XXX: Should we check for POLLERR? */
  -                    if (pollset[curr_pollfd].rtnevents & APR_POLLIN) {
  -                        last_pollfd = curr_pollfd;
  -                        offset = curr_pollfd;
  -                        goto got_fd;
  -                    }
  -                } while (curr_pollfd != last_pollfd);
   
  -                continue;
  +                /* We can always use pdesc[0], but sockets at position N
  +                 * could end up completely starved of attention in a very
  +                 * busy server. Therefore, we round-robin across the
  +                 * returned set of descriptors. While it is possible that
  +                 * the returned set of descriptors might flip around and
  +                 * continue to starve some sockets, we happen to know the
  +                 * internal pollset implementation retains ordering
  +                 * stability of the sockets. Thus, the round-robin should
  +                 * ensure that a socket will eventually be serviced.
  +                 */
  +                if (last_poll_idx >= numdesc)
  +                    last_poll_idx = 0;
  +
  +                /* Grab a listener record from the client_data of the poll
  +                 * descriptor, and advance our saved index to round-robin
  +                 * the next fetch.
  +                 *
  +                 * ### hmm... this descriptor might have POLLERR rather
  +                 * ### than POLLIN
  +                 */
  +                lr = pdesc[last_poll_idx++].client_data;
  +                goto got_fd;
               }
           }
       got_fd:
   	/* if we accept() something we don't want to die, so we have to
   	 * defer the exit
   	 */
  -        status = listensocks[offset].accept_func(&csd,
  -                                                 &listensocks[offset], ptrans);
  +        status = lr->accept_func(&csd, lr, ptrans);
  +
           SAFE_ACCEPT(accept_mutex_off());      /* unlock after "accept" */
   
           if (status == APR_EGENERAL) {
  
  
  

Mime
View raw message