mirror of
https://github.com/clearlinux/uwsgi.git
synced 2026-09-06 21:51:30 +00:00
httprouter keepalive preliminary support
This commit is contained in:
@@ -340,9 +340,19 @@ static void corerouter_expire_timeouts(struct uwsgi_corerouter *ucr) {
|
||||
}
|
||||
}
|
||||
|
||||
struct corerouter_session *corerouter_alloc_session(size_t size) {
|
||||
struct corerouter_session *corerouter_alloc_session(struct uwsgi_corerouter *ucr, struct uwsgi_gateway_socket *ugs, int new_connection, struct sockaddr *cr_addr, socklen_t cr_addr_len) {
|
||||
|
||||
return uwsgi_calloc(size);
|
||||
ucr->cr_table[new_connection] = uwsgi_calloc(ucr->session_size);
|
||||
ucr->cr_table[new_connection]->fd = new_connection;
|
||||
ucr->cr_table[new_connection]->instance_fd = -1;
|
||||
ucr->cr_table[new_connection]->status = COREROUTER_STATUS_RECV_HDR;
|
||||
|
||||
ucr->cr_table[new_connection]->timeout = cr_add_timeout(ucr, ucr->cr_table[new_connection]);
|
||||
|
||||
ucr->alloc_session(ucr, ugs, ucr->cr_table[new_connection], cr_addr, cr_addr_len);
|
||||
event_queue_add_fd_read(ucr->queue, new_connection);
|
||||
|
||||
return ucr->cr_table[new_connection];
|
||||
}
|
||||
|
||||
void uwsgi_corerouter_loop(int id, void *data) {
|
||||
@@ -530,16 +540,7 @@ void uwsgi_corerouter_loop(int id, void *data) {
|
||||
uwsgi_socket_b(new_connection);
|
||||
#endif
|
||||
|
||||
ucr->cr_table[new_connection] = corerouter_alloc_session(ucr->session_size);
|
||||
ucr->cr_table[new_connection]->fd = new_connection;
|
||||
ucr->cr_table[new_connection]->instance_fd = -1;
|
||||
ucr->cr_table[new_connection]->status = COREROUTER_STATUS_RECV_HDR;
|
||||
|
||||
ucr->cr_table[new_connection]->timeout = cr_add_timeout(ucr, ucr->cr_table[new_connection]);
|
||||
|
||||
ucr->alloc_session(ucr, ugs, ucr->cr_table[new_connection], (struct sockaddr *) &cr_addr, cr_addr_len);
|
||||
|
||||
event_queue_add_fd_read(ucr->queue, new_connection);
|
||||
corerouter_alloc_session(ucr, ugs, new_connection, (struct sockaddr *) &cr_addr, cr_addr_len);
|
||||
}
|
||||
else if (ugs->subscription) {
|
||||
uwsgi_corerouter_manage_subscription(ucr, id, ugs);
|
||||
|
||||
@@ -165,6 +165,7 @@ void uwsgi_corerouter_setup_sockets(struct uwsgi_corerouter *);
|
||||
|
||||
int uwsgi_corerouter_init(struct uwsgi_corerouter *);
|
||||
|
||||
struct corerouter_session *corerouter_alloc_session(struct uwsgi_corerouter *, struct uwsgi_gateway_socket *, int, struct sockaddr *, socklen_t);
|
||||
void corerouter_close_session(struct uwsgi_corerouter *, struct corerouter_session *);
|
||||
|
||||
int uwsgi_cr_map_use_void(struct uwsgi_corerouter *, struct corerouter_session *);
|
||||
|
||||
+24
-9
@@ -25,6 +25,7 @@ struct uwsgi_http {
|
||||
uint8_t modifier1;
|
||||
struct uwsgi_string_list *http_vars;
|
||||
int manage_expect;
|
||||
int keepalive;
|
||||
|
||||
} uhttp;
|
||||
|
||||
@@ -46,6 +47,7 @@ struct uwsgi_option http_options[] = {
|
||||
{"http-subscription-use-regexp", no_argument, 0, "enable regexp usage in subscription system", uwsgi_opt_true, &uhttp.cr.subscription_regexp, 0},
|
||||
{"http-timeout", required_argument, 0, "set internal http socket timeout", uwsgi_opt_set_int, &uhttp.cr.socket_timeout, 0},
|
||||
{"http-manage-expect", no_argument, 0, "manage the Expect HTTP request header", uwsgi_opt_true, &uhttp.manage_expect, 0},
|
||||
{"http-keepalive", no_argument, 0, "support HTTP keepalive requests", uwsgi_opt_true, &uhttp.keepalive, 0},
|
||||
|
||||
{"http-use-code-string", required_argument, 0, "use code string as hostname->server mapper for the http router", uwsgi_opt_corerouter_cs, &uhttp, 0},
|
||||
{"http-use-socket", optional_argument, 0, "forward request to the specified uwsgi socket", uwsgi_opt_corerouter_use_socket, &uhttp, 0},
|
||||
@@ -83,6 +85,7 @@ struct http_session {
|
||||
|
||||
size_t received_body;
|
||||
|
||||
|
||||
in_addr_t ip_addr;
|
||||
char ip[INET_ADDRSTRLEN];
|
||||
|
||||
@@ -568,6 +571,7 @@ void uwsgi_http_switch_events(struct uwsgi_corerouter *ucr, struct corerouter_se
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
// update transfer statistics
|
||||
if (cs->un)
|
||||
cs->un->transferred += len;
|
||||
@@ -576,6 +580,20 @@ void uwsgi_http_switch_events(struct uwsgi_corerouter *ucr, struct corerouter_se
|
||||
// body from client
|
||||
else if (interesting_fd == cs->fd) {
|
||||
|
||||
// Keep-Alive ?
|
||||
if (uhttp.keepalive && hs->received_body >= cs->post_cl) {
|
||||
// duplicate the socket
|
||||
int new_ka_connection = dup(cs->fd);
|
||||
if (new_ka_connection >= 0) {
|
||||
uwsgi_log("keepalive to %d\n", new_ka_connection);
|
||||
struct http_session *new_hs = (struct http_session *) corerouter_alloc_session(&uhttp.cr, NULL, new_ka_connection, NULL, -1);
|
||||
new_hs->ip_addr = hs->ip_addr;
|
||||
new_hs->port = hs->port;
|
||||
new_hs->port_len = hs->port_len;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
len = recv(cs->fd, bbuf, UMAX16, 0);
|
||||
#ifdef UWSGI_EVENT_USE_PORT
|
||||
event_queue_add_fd_read(uhttp_queue, cs->fd);
|
||||
@@ -588,15 +606,11 @@ void uwsgi_http_switch_events(struct uwsgi_corerouter *ucr, struct corerouter_se
|
||||
}
|
||||
|
||||
|
||||
if (hs->received_body >= cs->post_cl) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (len + hs->received_body > cs->post_cl) {
|
||||
len = cs->post_cl - hs->received_body;
|
||||
}
|
||||
|
||||
len = send(cs->instance_fd, hs->buffer, len, 0);
|
||||
len = send(cs->instance_fd, bbuf, len, 0);
|
||||
|
||||
if (len <= 0) {
|
||||
if (len < 0)
|
||||
@@ -612,7 +626,6 @@ void uwsgi_http_switch_events(struct uwsgi_corerouter *ucr, struct corerouter_se
|
||||
break;
|
||||
|
||||
|
||||
|
||||
// fallback to destroy !!!
|
||||
default:
|
||||
uwsgi_log("unknown event: closing session\n");
|
||||
@@ -631,11 +644,13 @@ void http_alloc_session(struct uwsgi_corerouter *ucr, struct uwsgi_gateway_socke
|
||||
struct http_session *hs = (struct http_session *) cs;
|
||||
hs->ptr = hs->buffer;
|
||||
cs->modifier1 = uhttp.modifier1;
|
||||
if (sa->sa_family == AF_INET) {
|
||||
if (sa && sa->sa_family == AF_INET) {
|
||||
hs->ip_addr = ((struct sockaddr_in *) sa)->sin_addr.s_addr;
|
||||
}
|
||||
hs->port = ugs->port;
|
||||
hs->port_len = ugs->port_len;
|
||||
if (ugs) {
|
||||
hs->port = ugs->port;
|
||||
hs->port_len = ugs->port_len;
|
||||
}
|
||||
}
|
||||
|
||||
int http_init() {
|
||||
|
||||
@@ -107,7 +107,7 @@ VALUE rb_uwsgi_io_read(VALUE obj, VALUE args) {
|
||||
struct wsgi_request *wsgi_req;
|
||||
Data_Get_Struct(obj, struct wsgi_request, wsgi_req);
|
||||
VALUE chunk;
|
||||
int chunk_size;
|
||||
unsigned int chunk_size;
|
||||
|
||||
if (!wsgi_req->post_cl || wsgi_req->buf_pos >= wsgi_req->post_cl) {
|
||||
/*
|
||||
@@ -130,7 +130,7 @@ VALUE rb_uwsgi_io_read(VALUE obj, VALUE args) {
|
||||
return chunk;
|
||||
}
|
||||
else if (RARRAY_LEN(args) > 0) {
|
||||
chunk_size = NUM2INT(RARRAY_PTR(args)[0]);
|
||||
chunk_size = NUM2UINT(RARRAY_PTR(args)[0]);
|
||||
if (wsgi_req->buf_pos+chunk_size > wsgi_req->post_cl) {
|
||||
chunk_size = wsgi_req->post_cl-wsgi_req->buf_pos;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user