⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 threaded.c

📁 Apache V2.0.15 Alpha For Linuxhttpd-2_0_15-alpha.tar.Z
💻 C
📖 第 1 页 / 共 4 页
字号:
#else    if (!one_process) {	apr_signal(SIGSEGV, sig_coredump);#ifdef SIGBUS	apr_signal(SIGBUS, sig_coredump);#endif /* SIGBUS */#ifdef SIGABORT	apr_signal(SIGABORT, sig_coredump);#endif /* SIGABORT */#ifdef SIGABRT	apr_signal(SIGABRT, sig_coredump);#endif /* SIGABRT */#ifdef SIGILL	apr_signal(SIGILL, sig_coredump);#endif /* SIGILL */#ifdef SIGXCPU	apr_signal(SIGXCPU, SIG_DFL);#endif /* SIGXCPU */#ifdef SIGXFSZ	apr_signal(SIGXFSZ, SIG_DFL);#endif /* SIGXFSZ */    }    apr_signal(SIGTERM, sig_term);#ifdef SIGHUP    apr_signal(SIGHUP, restart);#endif /* SIGHUP */#ifdef SIGWINCH    apr_signal(SIGWINCH, restart);#endif /* SIGWINCH */#ifdef SIGPIPE    apr_signal(SIGPIPE, SIG_IGN);#endif /* SIGPIPE */#endif}/***************************************************************** * Here follows a long bunch of generic server bookkeeping stuff... */int ap_graceful_stop_signalled(void){    /* XXX - Does this really work? - Manoj */    return is_graceful;}/***************************************************************** * Child process main loop. */static void process_socket(apr_pool_t *p, apr_socket_t *sock, int my_child_num, int my_thread_num){    conn_rec *current_conn;    long conn_id = AP_ID_FROM_CHILD_THREAD(my_child_num, my_thread_num);    int csd;    (void) apr_os_sock_get(&csd, sock);    if (csd >= FD_SETSIZE) {        ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING, 0, NULL,                     "new file descriptor %d is too large; you probably need "                     "to rebuild Apache with a larger FD_SETSIZE "                     "(currently %d)",                      csd, FD_SETSIZE);        apr_socket_close(sock);        return;    }    ap_sock_disable_nagle(sock);    current_conn = ap_new_connection(p, ap_server_conf, sock, conn_id);    if (current_conn) {        ap_process_connection(current_conn);        ap_lingering_close(current_conn);    }}/* Sets workers_may_exit if we received a character on the pipe_of_death */static void check_pipe_of_death(void){    apr_lock_acquire(pipe_of_death_mutex);    if (!workers_may_exit) {        apr_status_t ret;        char pipe_read_char;	apr_size_t n = 1;        ret = apr_recv(listensocks[0], &pipe_read_char, &n);        if (APR_STATUS_IS_EAGAIN(ret)) {            /* It lost the lottery. It must continue to suffer             * through a life of servitude. */        }        else {            /* It won the lottery (or something else is very             * wrong). Embrace death with open arms. */            workers_may_exit = 1;        }    }    apr_lock_release(pipe_of_death_mutex);}static void * worker_thread(void * dummy){    proc_info * ti = dummy;    int process_slot = ti->pid;    int thread_slot = ti->tid;    apr_pool_t *tpool = ti->tpool;    apr_socket_t *csd = NULL;    apr_pool_t *ptrans;		/* Pool for per-transaction stuff */    apr_socket_t *sd = NULL;    int n;    int curr_pollfd, last_pollfd = 0;    apr_pollfd_t *pollset;    apr_status_t rv;    free(ti);    apr_pool_create(&ptrans, tpool);    apr_lock_acquire(worker_thread_count_mutex);    worker_thread_count++;    apr_lock_release(worker_thread_count_mutex);    apr_poll_setup(&pollset, num_listensocks+1, tpool);    for(n=0 ; n <= num_listensocks ; ++n)	apr_poll_socket_add(pollset, listensocks[n], APR_POLLIN);    /* TODO: Switch to a system where threads reuse the results from earlier       poll calls - manoj */    while (1) {        workers_may_exit |= (ap_max_requests_per_child != 0) && (requests_this_child <= 0);        if (workers_may_exit) break;        (void) ap_update_child_status(process_slot, thread_slot, SERVER_READY,                                       (request_rec *) NULL);        if ((rv = SAFE_ACCEPT(apr_lock_acquire(accept_mutex)))            != APR_SUCCESS) {            ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                         "apr_lock_acquire failed. Attempting to shutdown "                         "process gracefully.");            workers_may_exit = 1;        }        while (!workers_may_exit) {	    apr_status_t ret;	    apr_int16_t event;            ret = apr_poll(pollset, &n, -1);            if (ret != APR_SUCCESS) {                if (APR_STATUS_IS_EINTR(ret)) {                    continue;                }                /* apr_poll() will only return errors in catastrophic                 * circumstances. Let's try exiting gracefully, for now. */                ap_log_error(APLOG_MARK, APLOG_ERR, ret, (const server_rec *)                             ap_server_conf, "apr_poll: (listen)");                workers_may_exit = 1;            }            if (workers_may_exit) break;	    apr_poll_revents_get(&event, listensocks[0], pollset);            if (event & APR_POLLIN) {                /* A process got a signal on the shutdown pipe. Check if we're                 * the lucky process to die. */                check_pipe_of_death();                continue;            }            if (num_listensocks == 1) {                sd = ap_listeners->sd;                goto got_fd;            }            else {                /* find a listener */                curr_pollfd = last_pollfd;                do {                    curr_pollfd++;                    if (curr_pollfd > num_listensocks) {                        curr_pollfd = 1;                    }                    /* XXX: Should we check for POLLERR? */		    apr_poll_revents_get(&event, listensocks[curr_pollfd], pollset);                    if (event & APR_POLLIN) {                        last_pollfd = curr_pollfd;			sd=listensocks[curr_pollfd];                        goto got_fd;                    }                } while (curr_pollfd != last_pollfd);            }        }    got_fd:        if (!workers_may_exit) {            if ((rv = apr_accept(&csd, sd, ptrans)) != APR_SUCCESS) {                csd = NULL;                ap_log_error(APLOG_MARK, APLOG_ERR, rv, ap_server_conf,                              "apr_accept");            }            if ((rv = SAFE_ACCEPT(apr_lock_release(accept_mutex)))                != APR_SUCCESS) {                ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                             "apr_lock_release failed. Attempting to shutdown "                             "process gracefully.");                workers_may_exit = 1;            }            if (csd != NULL) {                process_socket(ptrans, csd, process_slot, thread_slot);                requests_this_child--;            }        }        else {            if ((rv = SAFE_ACCEPT(apr_lock_release(accept_mutex)))                != APR_SUCCESS) {                ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                             "apr_lock_release failed. Attempting to shutdown "                             "process gracefully.");                workers_may_exit = 1;            }            break;        }        apr_pool_clear(ptrans);    }    apr_pool_destroy(tpool);    ap_update_child_status(process_slot, thread_slot, SERVER_DEAD,        (request_rec *) NULL);    apr_lock_acquire(worker_thread_count_mutex);    worker_thread_count--;    if (worker_thread_count == 0) {        /* All the threads have exited, now finish the shutdown process         * by signalling the sigwait thread */        kill(ap_my_pid, SIGTERM);    }    apr_lock_release(worker_thread_count_mutex);    return NULL;}static int check_signal(int signum){    switch (signum) {        case SIGTERM:        case SIGINT:            just_die(signum);            return 1;    }                                                                               return 0;}static void child_main(int child_num_arg){    apr_thread_t *thread;    apr_threadattr_t *thread_attr;    int i;    int my_child_num = child_num_arg;    proc_info *my_info = NULL;    ap_listen_rec *lr;    apr_status_t rv;    ap_my_pid = getpid();    apr_pool_create(&pchild, pconf);    /*stuff to do before we switch id's, so we have permissions.*/    reopen_scoreboard(pchild);    rv = SAFE_ACCEPT(apr_lock_child_init(&accept_mutex, lock_fname,                     pchild));    if (rv != APR_SUCCESS) {        ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                     "Couldn't initialize cross-process lock in child");        clean_child_exit(APEXIT_CHILDFATAL);    }    if (unixd_setup_child()) {	clean_child_exit(APEXIT_CHILDFATAL);    }    ap_run_child_init(pchild, ap_server_conf);    /*done with init critical section */    rv = apr_setup_signal_thread();    if (rv != APR_SUCCESS) {        ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                     "Couldn't initialize signal thread");        clean_child_exit(APEXIT_CHILDFATAL);    }    requests_this_child = ap_max_requests_per_child;        /* Set up the pollfd array */    listensocks = apr_pcalloc(pchild,			    sizeof(*listensocks) * (num_listensocks + 1));#if APR_FILES_AS_SOCKETS    apr_socket_from_file(&listensocks[0], pipe_of_death_in);#endif    for (lr = ap_listeners, i = 1; i <= num_listensocks; lr = lr->next, ++i)	listensocks[i]=lr->sd;    /* Setup worker threads */    worker_thread_count = 0;    apr_lock_create(&worker_thread_count_mutex, APR_MUTEX, APR_INTRAPROCESS,                    NULL, pchild);    apr_lock_create(&pipe_of_death_mutex, APR_MUTEX, APR_INTRAPROCESS,                     NULL, pchild);    apr_threadattr_create(&thread_attr, pchild);    apr_threadattr_detach_set(thread_attr);    rv = apr_create_signal_thread(&thread, thread_attr, check_signal, pchild);    if (rv != APR_SUCCESS) {        ap_log_error(APLOG_MARK, APLOG_EMERG, rv, ap_server_conf,                     "Couldn't create signal thread");        clean_child_exit(APEXIT_CHILDFATAL);    }    for (i=0; i < ap_threads_per_child - 1; i++) {	my_info = (proc_info *)malloc(sizeof(proc_info));        if (my_info == NULL) {            ap_log_error(APLOG_MARK, APLOG_ALERT, errno, ap_server_conf,		         "malloc: out of memory");            clean_child_exit(APEXIT_CHILDFATAL);        }	my_info->pid = my_child_num;        my_info->tid = i;	my_info->sd = 0;	apr_pool_create(&my_info->tpool, pchild);		/* We are creating threads right now */	(void) ap_update_child_status(my_child_num, i, SERVER_STARTING, 				      (request_rec *) NULL);	if ((rv = apr_thread_create(&thread, thread_attr, worker_thread, my_info, pchild))) {	    ap_log_error(APLOG_MARK, APLOG_ALERT, rv, ap_server_conf,			 "apr_thread_create: unable to create worker thread");            /* In case system resources are maxxed out, we don't want               Apache running away with the CPU trying to fork over and               over and over again if we exit. */            sleep(10);	    clean_child_exit(APEXIT_CHILDFATAL);	}	/* We let each thread update it's own scoreboard entry.  This is done	 * because it let's us deal with tid better.	 */    }    my_info = (proc_info *)malloc(sizeof(proc_info));    if (my_info == NULL) {        ap_log_error(APLOG_MARK, APLOG_ALERT, errno, ap_server_conf,                    "malloc: out of memory");        clean_child_exit(APEXIT_CHILDFATAL);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -