--- include/httpd.h (revision 1743254) +++ include/httpd.h (working copy) @@ -1083,6 +1083,9 @@ typedef enum { AP_CONN_KEEPALIVE } ap_conn_keepalive_e; +/* AP_SB_*_SIZE needed by conn_rec */ +#include "scoreboard.h" + /** * @brief Structure to store things which are per connection */ @@ -1183,6 +1186,10 @@ struct conn_rec { /** The "real" master connection. NULL if I am the master. */ conn_rec *master; + + /** Preserve scoreboard's worker last request infos */ + char sb_lastrline[AP_SB_RLINE_SIZE]; + char sb_lastvhost[AP_SB_VHOST_SIZE]; }; /** --- include/scoreboard.h (revision 1743254) +++ include/scoreboard.h (working copy) @@ -85,6 +85,9 @@ typedef enum { SB_SHARED = 2 } ap_scoreboard_e; +#define AP_SB_RLINE_SIZE 64 +#define AP_SB_VHOST_SIZE 32 + /* stuff which is worker specific */ typedef struct worker_score worker_score; struct worker_score { @@ -113,8 +116,8 @@ struct worker_score { struct tms times; #endif char client[32]; /* Keep 'em small... */ - char request[64]; /* We just want an idea... */ - char vhost[32]; /* What virtual host is being accessed? */ + char request[AP_SB_RLINE_SIZE]; /* We just want an idea... */ + char vhost[AP_SB_VHOST_SIZE]; /* What virtual host is being accessed? */ char protocol[16]; /* What protocol is used on the connection? */ }; --- modules/http/http_core.c (revision 1743254) +++ modules/http/http_core.c (working copy) @@ -148,7 +148,8 @@ static int ap_process_http_async_connection(conn_r c->keepalive = AP_CONN_UNKNOWN; /* process the request if it was read without error */ - ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, r); + ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, + r->the_request ? r : NULL); if (r->status == HTTP_OK) { cs->state = CONN_STATE_HANDLER; ap_process_async_request(r); @@ -203,7 +204,8 @@ static int ap_process_http_sync_connection(conn_re c->keepalive = AP_CONN_UNKNOWN; /* process the request if it was read without error */ - ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, r); + ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, + r->the_request ? r : NULL); if (r->status == HTTP_OK) { if (cs) cs->state = CONN_STATE_HANDLER; --- modules/http2/h2_conn_io.c (revision 1743254) +++ modules/http2/h2_conn_io.c (working copy) @@ -191,7 +191,7 @@ static apr_status_t pass_out(apr_bucket_brigade *b return APR_SUCCESS; } - ap_update_child_status_from_conn(c->sbh, SERVER_BUSY_WRITE, c); + ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, NULL); apr_brigade_length(bb, 0, &bblen); h2_conn_io_bb_log(c, 0, APLOG_TRACE2, "master conn pass", bb); status = ap_pass_brigade(c->output_filters, bb); --- modules/http2/h2_task.c (revision 1743254) +++ modules/http2/h2_task.c (working copy) @@ -235,7 +235,7 @@ static apr_status_t h2_task_process_request(h2_tas "h2_task(%s): create request_rec", task->id); r = h2_request_create_rec(req, c); if (r && (r->status == HTTP_OK)) { - ap_update_child_status(c->sbh, SERVER_BUSY_READ, r); + ap_update_child_status(c->sbh, SERVER_BUSY_WRITE, r); if (cs) { cs->state = CONN_STATE_HANDLER; --- server/connection.c (revision 1743254) +++ server/connection.c (working copy) @@ -101,7 +101,7 @@ AP_DECLARE(int) ap_prep_lingering_close(conn_rec * ap_run_pre_close_connection(c); if (c->sbh) { - ap_update_child_status(c->sbh, SERVER_CLOSING, NULL); + ap_update_child_status_from_conn(c->sbh, SERVER_CLOSING, c); } return 0; } --- server/core.c (revision 1743254) +++ server/core.c (working copy) @@ -4841,7 +4841,7 @@ static conn_rec *core_create_conn(apr_pool_t *ptra conn_rec *c = (conn_rec *) apr_pcalloc(ptrans, sizeof(conn_rec)); c->sbh = sbh; - (void)ap_update_child_status(c->sbh, SERVER_BUSY_READ, (request_rec *)NULL); + ap_update_child_status(c->sbh, SERVER_BUSY_READ, NULL); /* Got a connection structure, so initialize what fields we can * (the rest are zeroed out by pcalloc). --- server/mpm/event/event.c (revision 1743254) +++ server/mpm/event/event.c (working copy) @@ -1114,7 +1114,7 @@ read_request: if (cs->pub.state == CONN_STATE_WRITE_COMPLETION) { ap_filter_t *output_filter = c->output_filters; apr_status_t rv; - ap_update_child_status_from_conn(sbh, SERVER_BUSY_WRITE, c); + ap_update_child_status(sbh, SERVER_BUSY_WRITE, NULL); while (output_filter->next != NULL) { output_filter = output_filter->next; } @@ -1910,7 +1910,8 @@ static void *APR_THREAD_FUNC worker_thread(apr_thr } ap_update_child_status_from_indexes(process_slot, thread_slot, - dying ? SERVER_GRACEFUL : SERVER_READY, NULL); + dying ? SERVER_GRACEFUL + : SERVER_READY, NULL); worker_pop: if (workers_may_exit) { break; @@ -1965,9 +1966,8 @@ static void *APR_THREAD_FUNC worker_thread(apr_thr } ap_update_child_status_from_indexes(process_slot, thread_slot, - dying ? SERVER_DEAD : - SERVER_GRACEFUL, - (request_rec *) NULL); + dying ? SERVER_DEAD + : SERVER_GRACEFUL, NULL); apr_thread_exit(thd, APR_SUCCESS); return NULL; @@ -2728,8 +2728,7 @@ static void server_main_loop(int remaining_childre for (i = 0; i < threads_per_child; i++) ap_update_child_status_from_indexes(child_slot, i, - SERVER_DEAD, - (request_rec *) NULL); + SERVER_DEAD, NULL); event_note_child_killed(child_slot, 0, 0); ps = &ap_scoreboard_image->parent[child_slot]; --- server/mpm/winnt/child.c (revision 1743254) +++ server/mpm/winnt/child.c (working copy) @@ -894,8 +894,7 @@ static DWORD __stdcall worker_main(void *thread_nu } } - ap_update_child_status_from_indexes(0, thread_num, SERVER_DEAD, - (request_rec *) NULL); + ap_update_child_status_from_indexes(0, thread_num, SERVER_DEAD, NULL); return 0; } @@ -1314,13 +1313,13 @@ void child_main(apr_pool_t *pconf, DWORD parent_pi threads_created); } for (i = 0; i < threads_created; i++) { - int *score_idx; + int *idx; TerminateThread(child_handles[i], 1); CloseHandle(child_handles[i]); /* Reset the scoreboard entry for the thread we just whacked */ - score_idx = apr_hash_get(ht, &child_handles[i], sizeof(HANDLE)); - if (score_idx) { - ap_update_child_status_from_indexes(0, *score_idx, SERVER_DEAD, NULL); + idx = apr_hash_get(ht, &child_handles[i], sizeof(HANDLE)); + if (idx) { + ap_update_child_status_from_indexes(0, *idx, SERVER_DEAD, NULL); } } ap_log_error(APLOG_MARK, APLOG_NOTICE, APR_SUCCESS, ap_server_conf, APLOGNO(00364) --- server/mpm/worker/worker.c (revision 1743254) +++ server/mpm/worker/worker.c (working copy) @@ -928,7 +928,8 @@ static void * APR_THREAD_FUNC worker_thread(apr_th ap_scoreboard_image->servers[process_slot][thread_slot].pid = ap_my_pid; ap_scoreboard_image->servers[process_slot][thread_slot].tid = apr_os_thread_current(); ap_scoreboard_image->servers[process_slot][thread_slot].generation = retained->my_generation; - ap_update_child_status_from_indexes(process_slot, thread_slot, SERVER_STARTING, NULL); + ap_update_child_status_from_indexes(process_slot, thread_slot, + SERVER_STARTING, NULL); #ifdef HAVE_PTHREAD_KILL unblock_signal(WORKER_SIGNAL); @@ -949,7 +950,8 @@ static void * APR_THREAD_FUNC worker_thread(apr_th is_idle = 1; } - ap_update_child_status_from_indexes(process_slot, thread_slot, SERVER_READY, NULL); + ap_update_child_status_from_indexes(process_slot, thread_slot, + SERVER_READY, NULL); worker_pop: if (workers_may_exit) { break; @@ -995,7 +997,8 @@ worker_pop: } ap_update_child_status_from_indexes(process_slot, thread_slot, - (dying) ? SERVER_DEAD : SERVER_GRACEFUL, (request_rec *) NULL); + dying ? SERVER_DEAD + : SERVER_GRACEFUL, NULL); apr_thread_exit(thd, APR_SUCCESS); return NULL; @@ -1730,8 +1733,8 @@ static void server_main_loop(int remaining_childre process_score *ps; for (i = 0; i < threads_per_child; i++) - ap_update_child_status_from_indexes(child_slot, i, SERVER_DEAD, - (request_rec *) NULL); + ap_update_child_status_from_indexes(child_slot, i, + SERVER_DEAD, NULL); worker_note_child_killed(child_slot, 0, 0); ps = &ap_scoreboard_image->parent[child_slot]; --- server/protocol.c (revision 1743254) +++ server/protocol.c (working copy) @@ -992,7 +992,7 @@ request_rec *ap_read_request(conn_rec *conn) goto traceout; } else if (r->status == HTTP_REQUEST_TIME_OUT) { - ap_update_child_status(conn->sbh, SERVER_BUSY_LOG, r); + ap_update_child_status(conn->sbh, SERVER_BUSY_LOG, NULL); if (!r->connection->keepalives) { ap_run_log_transaction(r); } --- server/scoreboard.c (revision 1743254) +++ server/scoreboard.c (working copy) @@ -464,22 +464,18 @@ static int update_child_status_internal(int child_ { int old_status; worker_score *ws; - process_score *ps; int mpm_generation; ws = &ap_scoreboard_image->servers[child_num][thread_num]; old_status = ws->status; - if (status >= 0) { - ws->status = status; - - ps = &ap_scoreboard_image->parent[child_num]; - - if (status == SERVER_READY - && old_status == SERVER_STARTING) { - ws->thread_num = child_num * thread_limit + thread_num; - ap_mpm_query(AP_MPMQ_GENERATION, &mpm_generation); - ps->generation = mpm_generation; - } + ws->status = status; + + if (status == SERVER_READY + && old_status == SERVER_STARTING) { + process_score *ps = &ap_scoreboard_image->parent[child_num]; + ws->thread_num = child_num * thread_limit + thread_num; + ap_mpm_query(AP_MPMQ_GENERATION, &mpm_generation); + ps->generation = mpm_generation; } if (ap_extended_status) { @@ -497,46 +493,51 @@ static int update_child_status_internal(int child_ ws->conn_bytes = 0; ws->last_used = apr_time_now(); } - if (status == SERVER_READY) { - ws->client[0]='\0'; - ws->vhost[0]='\0'; - ws->request[0]='\0'; - ws->protocol[0]='\0'; + + if (descr) { + apr_cpystrn(ws->request, descr, sizeof(ws->request)); } - else { - if (descr) { - apr_cpystrn(ws->request, descr, sizeof(ws->request)); + else if (r) { + copy_request(ws->request, sizeof(ws->request), r); + apr_cpystrn(c->sb_lastrline, ws->request, sizeof(c->sb_lastrline)); + } + else if (c) { + apr_cpystrn(ws->request, c->sb_lastrline, sizeof(ws->request)); + } + + if (r && r->useragent_ip) { + if (!(val = ap_get_useragent_host(r, REMOTE_NOLOOKUP, NULL))) + apr_cpystrn(ws->client, r->useragent_ip, sizeof(ws->client)); + else + apr_cpystrn(ws->client, val, sizeof(ws->client)); + } + else if (c) { + if (!(val = ap_get_remote_host(c, c->base_server->lookup_defaults, + REMOTE_NOLOOKUP, NULL))) + apr_cpystrn(ws->client, c->client_ip, sizeof(ws->client)); + else + apr_cpystrn(ws->client, val, sizeof(ws->client)); + } + + if (s) { + if (c) { + apr_snprintf(ws->vhost, sizeof(ws->vhost), "%s:%d", + s->server_hostname, c->local_addr->port); + apr_cpystrn(c->sb_lastvhost, ws->vhost, + sizeof(c->sb_lastvhost)); } - else if (r) { - copy_request(ws->request, sizeof(ws->request), r); + else { + apr_cpystrn(ws->vhost, s->server_hostname, sizeof(ws->vhost)); } - if (r) { - if (!(val = ap_get_useragent_host(r, REMOTE_NOLOOKUP, NULL))) - apr_cpystrn(ws->client, r->useragent_ip, sizeof(ws->client)); - else - apr_cpystrn(ws->client, val, sizeof(ws->client)); - } - else if (c) { - if (!(val = ap_get_remote_host(c, c->base_server->lookup_defaults, - REMOTE_NOLOOKUP, NULL))) - apr_cpystrn(ws->client, c->client_ip, sizeof(ws->client)); - else - apr_cpystrn(ws->client, val, sizeof(ws->client)); - } - if (s) { - if (c) { - apr_snprintf(ws->vhost, sizeof(ws->vhost), "%s:%d", - s->server_hostname, c->local_addr->port); - } - else { - apr_cpystrn(ws->vhost, s->server_hostname, sizeof(ws->vhost)); - } - } - if (c) { - val = ap_get_protocol(c); - apr_cpystrn(ws->protocol, val, sizeof(ws->protocol)); - } } + else if (c) { + apr_cpystrn(ws->vhost, c->sb_lastvhost, sizeof(ws->vhost)); + } + + if (c) { + val = ap_get_protocol(c); + apr_cpystrn(ws->protocol, val, sizeof(ws->protocol)); + } } return old_status;