From 9fe4b7b14ac1034f70dae7de7a02ae0ffdf82ede Mon Sep 17 00:00:00 2001 From: Glenn Maynard Date: Tue, 13 May 2014 16:25:17 +0000 Subject: [PATCH] Add ELB proxy protocol support to the HTTP module. Previously, this was only supported with http-socket. If you're using http-socket, you probably have a webserver on top of you--and if you have that, then uWSGI isn't receiving the proxy protocol anyway. --- plugins/http/http.c | 26 ++++++++++++++++++++++++-- proto/http.c | 2 +- uwsgi.h | 1 + 3 files changed, 26 insertions(+), 3 deletions(-) diff --git a/plugins/http/http.c b/plugins/http/http.c index 9532166f..4bbe51ae 100644 --- a/plugins/http/http.c +++ b/plugins/http/http.c @@ -195,6 +195,14 @@ int http_headers_parse(struct corerouter_peer *peer) { char *watermark = ptr + hr->headers_size; char *base = ptr; char *query_string = NULL; + char *proxy_src = NULL; + char *proxy_dst = NULL; + char *proxy_src_port = NULL; + char *proxy_dst_port = NULL; + uint16_t proxy_src_len = 0; + uint16_t proxy_dst_len = 0; + uint16_t proxy_src_port_len = 0; + uint16_t proxy_dst_port_len = 0; peer->out = uwsgi_buffer_new(uwsgi.page_size); // force this buffer to be destroyed as soon as possibile @@ -207,6 +215,11 @@ int http_headers_parse(struct corerouter_peer *peer) { struct uwsgi_buffer *out = peer->out; int found = 0; + if (uwsgi.enable_proxy_protocol) { + ptr = proxy1_parse(ptr, watermark, &proxy_src, &proxy_src_len, &proxy_dst, &proxy_dst_len, &proxy_src_port, &proxy_src_port_len, &proxy_dst_port, &proxy_dst_port_len); + base = ptr; + } + // REQUEST_METHOD while (ptr < watermark) { if (*ptr == ' ') { @@ -338,8 +351,17 @@ int http_headers_parse(struct corerouter_peer *peer) { #endif // REMOTE_ADDR - if (uwsgi_buffer_append_keyval(out, "REMOTE_ADDR", 11, peer->session->client_address, strlen(peer->session->client_address))) return -1; - if (uwsgi_buffer_append_keyval(out, "REMOTE_PORT", 11, peer->session->client_port, strlen(peer->session->client_port))) return -1; + if (proxy_src) { + if (uwsgi_buffer_append_keyval(out, "REMOTE_ADDR", 11, proxy_src, proxy_src_len)) return -1; + if (proxy_src_port) { + if (uwsgi_buffer_append_keyval(out, "REMOTE_PORT", 11, proxy_src_port, proxy_src_port_len)) return -1; + } + } + else + { + if (uwsgi_buffer_append_keyval(out, "REMOTE_ADDR", 11, peer->session->client_address, strlen(peer->session->client_address))) return -1; + if (uwsgi_buffer_append_keyval(out, "REMOTE_PORT", 11, peer->session->client_port, strlen(peer->session->client_port))) return -1; + } //HEADERS base = ptr; diff --git a/proto/http.c b/proto/http.c index 5562cad5..1338b9ff 100644 --- a/proto/http.c +++ b/proto/http.c @@ -79,7 +79,7 @@ static uint16_t http_add_uwsgi_header(struct wsgi_request *wsgi_req, char *hh, s return 2 + keylen + 2 + hvlen; } -static char *proxy1_parse(char *ptr, char *watermark, char **src, uint16_t *src_len, char **dst, uint16_t *dst_len, char **src_port, uint16_t *src_port_len, char **dst_port, uint16_t *dst_port_len) { +char *proxy1_parse(char *ptr, char *watermark, char **src, uint16_t *src_len, char **dst, uint16_t *dst_len, char **src_port, uint16_t *src_port_len, char **dst_port, uint16_t *dst_port_len) { // check for PROXY header if (watermark - ptr > 6) { if (memcmp(ptr, "PROXY ", 6)) return ptr; diff --git a/uwsgi.h b/uwsgi.h index fec4270b..4542326b 100644 --- a/uwsgi.h +++ b/uwsgi.h @@ -4441,6 +4441,7 @@ int uwsgi_exceptions_catch(struct wsgi_request *); uint64_t uwsgi_worker_exceptions(int); struct uwsgi_exception_handler *uwsgi_register_exception_handler(char *, int (*)(struct uwsgi_exception_handler_instance *, char *, size_t)); +char *proxy1_parse(char *ptr, char *watermark, char **src, uint16_t *src_len, char **dst, uint16_t *dst_len, char **src_port, uint16_t *src_port_len, char **dst_port, uint16_t *dst_port_len); void uwsgi_async_queue_is_full(time_t); char *uwsgi_get_header(struct wsgi_request *, char *, uint16_t, uint16_t *);