Home | History | Annotate | Line # | Download | only in dist
http.c revision 1.1.1.1
      1 /*	$NetBSD: http.c,v 1.1.1.1 2009/11/02 10:01:01 plunky Exp $	*/
      2 /*
      3  * Copyright (c) 2002-2006 Niels Provos <provos (at) citi.umich.edu>
      4  * All rights reserved.
      5  *
      6  * Redistribution and use in source and binary forms, with or without
      7  * modification, are permitted provided that the following conditions
      8  * are met:
      9  * 1. Redistributions of source code must retain the above copyright
     10  *    notice, this list of conditions and the following disclaimer.
     11  * 2. Redistributions in binary form must reproduce the above copyright
     12  *    notice, this list of conditions and the following disclaimer in the
     13  *    documentation and/or other materials provided with the distribution.
     14  * 3. The name of the author may not be used to endorse or promote products
     15  *    derived from this software without specific prior written permission.
     16  *
     17  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
     18  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
     19  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
     20  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
     21  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
     22  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     23  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     24  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
     26  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     27  */
     28 
     29 #ifdef HAVE_CONFIG_H
     30 #include "config.h"
     31 #endif
     32 
     33 #ifdef HAVE_SYS_PARAM_H
     34 #include <sys/param.h>
     35 #endif
     36 #ifdef HAVE_SYS_TYPES_H
     37 #include <sys/types.h>
     38 #endif
     39 
     40 #ifdef HAVE_SYS_TIME_H
     41 #include <sys/time.h>
     42 #endif
     43 #ifdef HAVE_SYS_IOCCOM_H
     44 #include <sys/ioccom.h>
     45 #endif
     46 
     47 #ifndef WIN32
     48 #include <sys/resource.h>
     49 #include <sys/socket.h>
     50 #include <sys/stat.h>
     51 #include <sys/wait.h>
     52 #endif
     53 
     54 #include <sys/queue.h>
     55 
     56 #ifndef WIN32
     57 #include <netinet/in.h>
     58 #include <netdb.h>
     59 #endif
     60 
     61 #ifdef WIN32
     62 #include <winsock2.h>
     63 #endif
     64 
     65 #include <assert.h>
     66 #include <ctype.h>
     67 #include <errno.h>
     68 #include <stdio.h>
     69 #include <stdlib.h>
     70 #include <string.h>
     71 #ifndef WIN32
     72 #include <syslog.h>
     73 #endif
     74 #include <signal.h>
     75 #include <time.h>
     76 #ifdef HAVE_UNISTD_H
     77 #include <unistd.h>
     78 #endif
     79 #ifdef HAVE_FCNTL_H
     80 #include <fcntl.h>
     81 #endif
     82 
     83 #undef timeout_pending
     84 #undef timeout_initialized
     85 
     86 #include "strlcpy-internal.h"
     87 #include "event.h"
     88 #include "evhttp.h"
     89 #include "evutil.h"
     90 #include "log.h"
     91 #include "http-internal.h"
     92 
     93 #ifdef WIN32
     94 #define strcasecmp _stricmp
     95 #define strncasecmp _strnicmp
     96 #define strdup _strdup
     97 #endif
     98 
     99 #ifndef HAVE_GETNAMEINFO
    100 #define NI_MAXSERV 32
    101 #define NI_MAXHOST 1025
    102 
    103 #define NI_NUMERICHOST 1
    104 #define NI_NUMERICSERV 2
    105 
    106 static int
    107 fake_getnameinfo(const struct sockaddr *sa, size_t salen, char *host,
    108 	size_t hostlen, char *serv, size_t servlen, int flags)
    109 {
    110         struct sockaddr_in *sin = (struct sockaddr_in *)sa;
    111 
    112         if (serv != NULL) {
    113 				char tmpserv[16];
    114 				evutil_snprintf(tmpserv, sizeof(tmpserv),
    115 					"%d", ntohs(sin->sin_port));
    116                 if (strlcpy(serv, tmpserv, servlen) >= servlen)
    117                         return (-1);
    118         }
    119 
    120         if (host != NULL) {
    121                 if (flags & NI_NUMERICHOST) {
    122                         if (strlcpy(host, inet_ntoa(sin->sin_addr),
    123                             hostlen) >= hostlen)
    124                                 return (-1);
    125                         else
    126                                 return (0);
    127                 } else {
    128 						struct hostent *hp;
    129                         hp = gethostbyaddr((char *)&sin->sin_addr,
    130                             sizeof(struct in_addr), AF_INET);
    131                         if (hp == NULL)
    132                                 return (-2);
    133 
    134                         if (strlcpy(host, hp->h_name, hostlen) >= hostlen)
    135                                 return (-1);
    136                         else
    137                                 return (0);
    138                 }
    139         }
    140         return (0);
    141 }
    142 
    143 #endif
    144 
    145 #ifndef HAVE_GETADDRINFO
    146 struct addrinfo {
    147 	int ai_family;
    148 	int ai_socktype;
    149 	int ai_protocol;
    150 	size_t ai_addrlen;
    151 	struct sockaddr *ai_addr;
    152 	struct addrinfo *ai_next;
    153 };
    154 static int
    155 fake_getaddrinfo(const char *hostname, struct addrinfo *ai)
    156 {
    157 	struct hostent *he = NULL;
    158 	struct sockaddr_in *sa;
    159 	if (hostname) {
    160 		he = gethostbyname(hostname);
    161 		if (!he)
    162 			return (-1);
    163 	}
    164 	ai->ai_family = he ? he->h_addrtype : AF_INET;
    165 	ai->ai_socktype = SOCK_STREAM;
    166 	ai->ai_protocol = 0;
    167 	ai->ai_addrlen = sizeof(struct sockaddr_in);
    168 	if (NULL == (ai->ai_addr = malloc(ai->ai_addrlen)))
    169 		return (-1);
    170 	sa = (struct sockaddr_in*)ai->ai_addr;
    171 	memset(sa, 0, ai->ai_addrlen);
    172 	if (he) {
    173 		sa->sin_family = he->h_addrtype;
    174 		memcpy(&sa->sin_addr, he->h_addr_list[0], he->h_length);
    175 	} else {
    176 		sa->sin_family = AF_INET;
    177 		sa->sin_addr.s_addr = INADDR_ANY;
    178 	}
    179 	ai->ai_next = NULL;
    180 	return (0);
    181 }
    182 static void
    183 fake_freeaddrinfo(struct addrinfo *ai)
    184 {
    185 	free(ai->ai_addr);
    186 }
    187 #endif
    188 
    189 #ifndef MIN
    190 #define MIN(a,b) (((a)<(b))?(a):(b))
    191 #endif
    192 
    193 /* wrapper for setting the base from the http server */
    194 #define EVHTTP_BASE_SET(x, y) do { \
    195 	if ((x)->base != NULL) event_base_set((x)->base, y);	\
    196 } while (0)
    197 
    198 extern int debug;
    199 
    200 static int socket_connect(int fd, const char *address, unsigned short port);
    201 static int bind_socket_ai(struct addrinfo *, int reuse);
    202 static int bind_socket(const char *, u_short, int reuse);
    203 static void name_from_addr(struct sockaddr *, socklen_t, char **, char **);
    204 static int evhttp_associate_new_request_with_connection(
    205 	struct evhttp_connection *evcon);
    206 static void evhttp_connection_start_detectclose(
    207 	struct evhttp_connection *evcon);
    208 static void evhttp_connection_stop_detectclose(
    209 	struct evhttp_connection *evcon);
    210 static void evhttp_request_dispatch(struct evhttp_connection* evcon);
    211 static void evhttp_read_firstline(struct evhttp_connection *evcon,
    212 				  struct evhttp_request *req);
    213 static void evhttp_read_header(struct evhttp_connection *evcon,
    214     struct evhttp_request *req);
    215 static int evhttp_add_header_internal(struct evkeyvalq *headers,
    216     const char *key, const char *value);
    217 static int evhttp_decode_uri_internal(const char *uri, size_t length,
    218     char *ret, int always_decode_plus);
    219 
    220 void evhttp_read(int, short, void *);
    221 void evhttp_write(int, short, void *);
    222 
    223 #ifndef HAVE_STRSEP
    224 /* strsep replacement for platforms that lack it.  Only works if
    225  * del is one character long. */
    226 static char *
    227 strsep(char **s, const char *del)
    228 {
    229 	char *d, *tok;
    230 	assert(strlen(del) == 1);
    231 	if (!s || !*s)
    232 		return NULL;
    233 	tok = *s;
    234 	d = strstr(tok, del);
    235 	if (d) {
    236 		*d = '\0';
    237 		*s = d + 1;
    238 	} else
    239 		*s = NULL;
    240 	return tok;
    241 }
    242 #endif
    243 
    244 static const char *
    245 html_replace(char ch, char *buf)
    246 {
    247 	switch (ch) {
    248 	case '<':
    249 		return "&lt;";
    250 	case '>':
    251 		return "&gt;";
    252 	case '"':
    253 		return "&quot;";
    254 	case '\'':
    255 		return "&#039;";
    256 	case '&':
    257 		return "&amp;";
    258 	default:
    259 		break;
    260 	}
    261 
    262 	/* Echo the character back */
    263 	buf[0] = ch;
    264 	buf[1] = '\0';
    265 
    266 	return buf;
    267 }
    268 
    269 /*
    270  * Replaces <, >, ", ' and & with &lt;, &gt;, &quot;,
    271  * &#039; and &amp; correspondingly.
    272  *
    273  * The returned string needs to be freed by the caller.
    274  */
    275 
    276 char *
    277 evhttp_htmlescape(const char *html)
    278 {
    279 	int i, new_size = 0, old_size = strlen(html);
    280 	char *escaped_html, *p;
    281 	char scratch_space[2];
    282 
    283 	for (i = 0; i < old_size; ++i)
    284           new_size += strlen(html_replace(html[i], scratch_space));
    285 
    286 	p = escaped_html = malloc(new_size + 1);
    287 	if (escaped_html == NULL)
    288 		event_err(1, "%s: malloc(%d)", __func__, new_size + 1);
    289 	for (i = 0; i < old_size; ++i) {
    290 		const char *replaced = html_replace(html[i], scratch_space);
    291 		/* this is length checked */
    292 		strcpy(p, replaced);
    293 		p += strlen(replaced);
    294 	}
    295 
    296 	*p = '\0';
    297 
    298 	return (escaped_html);
    299 }
    300 
    301 static const char *
    302 evhttp_method(enum evhttp_cmd_type type)
    303 {
    304 	const char *method;
    305 
    306 	switch (type) {
    307 	case EVHTTP_REQ_GET:
    308 		method = "GET";
    309 		break;
    310 	case EVHTTP_REQ_POST:
    311 		method = "POST";
    312 		break;
    313 	case EVHTTP_REQ_HEAD:
    314 		method = "HEAD";
    315 		break;
    316 	default:
    317 		method = NULL;
    318 		break;
    319 	}
    320 
    321 	return (method);
    322 }
    323 
    324 static void
    325 evhttp_add_event(struct event *ev, int timeout, int default_timeout)
    326 {
    327 	if (timeout != 0) {
    328 		struct timeval tv;
    329 
    330 		evutil_timerclear(&tv);
    331 		tv.tv_sec = timeout != -1 ? timeout : default_timeout;
    332 		event_add(ev, &tv);
    333 	} else {
    334 		event_add(ev, NULL);
    335 	}
    336 }
    337 
    338 void
    339 evhttp_write_buffer(struct evhttp_connection *evcon,
    340     void (*cb)(struct evhttp_connection *, void *), void *arg)
    341 {
    342 	event_debug(("%s: preparing to write buffer\n", __func__));
    343 
    344 	/* Set call back */
    345 	evcon->cb = cb;
    346 	evcon->cb_arg = arg;
    347 
    348 	/* check if the event is already pending */
    349 	if (event_pending(&evcon->ev, EV_WRITE|EV_TIMEOUT, NULL))
    350 		event_del(&evcon->ev);
    351 
    352 	event_set(&evcon->ev, evcon->fd, EV_WRITE, evhttp_write, evcon);
    353 	EVHTTP_BASE_SET(evcon, &evcon->ev);
    354 	evhttp_add_event(&evcon->ev, evcon->timeout, HTTP_WRITE_TIMEOUT);
    355 }
    356 
    357 static int
    358 evhttp_connected(struct evhttp_connection *evcon)
    359 {
    360 	switch (evcon->state) {
    361 	case EVCON_DISCONNECTED:
    362 	case EVCON_CONNECTING:
    363 		return (0);
    364 	case EVCON_IDLE:
    365 	case EVCON_READING_FIRSTLINE:
    366 	case EVCON_READING_HEADERS:
    367 	case EVCON_READING_BODY:
    368 	case EVCON_READING_TRAILER:
    369 	case EVCON_WRITING:
    370 	default:
    371 		return (1);
    372 	}
    373 }
    374 
    375 /*
    376  * Create the headers needed for an HTTP request
    377  */
    378 static void
    379 evhttp_make_header_request(struct evhttp_connection *evcon,
    380     struct evhttp_request *req)
    381 {
    382 	const char *method;
    383 
    384 	evhttp_remove_header(req->output_headers, "Proxy-Connection");
    385 
    386 	/* Generate request line */
    387 	method = evhttp_method(req->type);
    388 	evbuffer_add_printf(evcon->output_buffer, "%s %s HTTP/%d.%d\r\n",
    389 	    method, req->uri, req->major, req->minor);
    390 
    391 	/* Add the content length on a post request if missing */
    392 	if (req->type == EVHTTP_REQ_POST &&
    393 	    evhttp_find_header(req->output_headers, "Content-Length") == NULL){
    394 		char size[12];
    395 		evutil_snprintf(size, sizeof(size), "%ld",
    396 		    (long)EVBUFFER_LENGTH(req->output_buffer));
    397 		evhttp_add_header(req->output_headers, "Content-Length", size);
    398 	}
    399 }
    400 
    401 static int
    402 evhttp_is_connection_close(int flags, struct evkeyvalq* headers)
    403 {
    404 	if (flags & EVHTTP_PROXY_REQUEST) {
    405 		/* proxy connection */
    406 		const char *connection = evhttp_find_header(headers, "Proxy-Connection");
    407 		return (connection == NULL || strcasecmp(connection, "keep-alive") != 0);
    408 	} else {
    409 		const char *connection = evhttp_find_header(headers, "Connection");
    410 		return (connection != NULL && strcasecmp(connection, "close") == 0);
    411 	}
    412 }
    413 
    414 static int
    415 evhttp_is_connection_keepalive(struct evkeyvalq* headers)
    416 {
    417 	const char *connection = evhttp_find_header(headers, "Connection");
    418 	return (connection != NULL
    419 	    && strncasecmp(connection, "keep-alive", 10) == 0);
    420 }
    421 
    422 static void
    423 evhttp_maybe_add_date_header(struct evkeyvalq *headers)
    424 {
    425 	if (evhttp_find_header(headers, "Date") == NULL) {
    426 		char date[50];
    427 #ifndef WIN32
    428 		struct tm cur;
    429 #endif
    430 		struct tm *cur_p;
    431 		time_t t = time(NULL);
    432 #ifdef WIN32
    433 		cur_p = gmtime(&t);
    434 #else
    435 		gmtime_r(&t, &cur);
    436 		cur_p = &cur;
    437 #endif
    438 		if (strftime(date, sizeof(date),
    439 			"%a, %d %b %Y %H:%M:%S GMT", cur_p) != 0) {
    440 			evhttp_add_header(headers, "Date", date);
    441 		}
    442 	}
    443 }
    444 
    445 static void
    446 evhttp_maybe_add_content_length_header(struct evkeyvalq *headers,
    447     long content_length)
    448 {
    449 	if (evhttp_find_header(headers, "Transfer-Encoding") == NULL &&
    450 	    evhttp_find_header(headers,	"Content-Length") == NULL) {
    451 		char len[12];
    452 		evutil_snprintf(len, sizeof(len), "%ld", content_length);
    453 		evhttp_add_header(headers, "Content-Length", len);
    454 	}
    455 }
    456 
    457 /*
    458  * Create the headers needed for an HTTP reply
    459  */
    460 
    461 static void
    462 evhttp_make_header_response(struct evhttp_connection *evcon,
    463     struct evhttp_request *req)
    464 {
    465 	int is_keepalive = evhttp_is_connection_keepalive(req->input_headers);
    466 	evbuffer_add_printf(evcon->output_buffer, "HTTP/%d.%d %d %s\r\n",
    467 	    req->major, req->minor, req->response_code,
    468 	    req->response_code_line);
    469 
    470 	if (req->major == 1) {
    471 		if (req->minor == 1)
    472 			evhttp_maybe_add_date_header(req->output_headers);
    473 
    474 		/*
    475 		 * if the protocol is 1.0; and the connection was keep-alive
    476 		 * we need to add a keep-alive header, too.
    477 		 */
    478 		if (req->minor == 0 && is_keepalive)
    479 			evhttp_add_header(req->output_headers,
    480 			    "Connection", "keep-alive");
    481 
    482 		if (req->minor == 1 || is_keepalive) {
    483 			/*
    484 			 * we need to add the content length if the
    485 			 * user did not give it, this is required for
    486 			 * persistent connections to work.
    487 			 */
    488 			evhttp_maybe_add_content_length_header(
    489 				req->output_headers,
    490 				(long)EVBUFFER_LENGTH(req->output_buffer));
    491 		}
    492 	}
    493 
    494 	/* Potentially add headers for unidentified content. */
    495 	if (EVBUFFER_LENGTH(req->output_buffer)) {
    496 		if (evhttp_find_header(req->output_headers,
    497 			"Content-Type") == NULL) {
    498 			evhttp_add_header(req->output_headers,
    499 			    "Content-Type", "text/html; charset=ISO-8859-1");
    500 		}
    501 	}
    502 
    503 	/* if the request asked for a close, we send a close, too */
    504 	if (evhttp_is_connection_close(req->flags, req->input_headers)) {
    505 		evhttp_remove_header(req->output_headers, "Connection");
    506 		if (!(req->flags & EVHTTP_PROXY_REQUEST))
    507 		    evhttp_add_header(req->output_headers, "Connection", "close");
    508 		evhttp_remove_header(req->output_headers, "Proxy-Connection");
    509 	}
    510 }
    511 
    512 void
    513 evhttp_make_header(struct evhttp_connection *evcon, struct evhttp_request *req)
    514 {
    515 	struct evkeyval *header;
    516 
    517 	/*
    518 	 * Depending if this is a HTTP request or response, we might need to
    519 	 * add some new headers or remove existing headers.
    520 	 */
    521 	if (req->kind == EVHTTP_REQUEST) {
    522 		evhttp_make_header_request(evcon, req);
    523 	} else {
    524 		evhttp_make_header_response(evcon, req);
    525 	}
    526 
    527 	TAILQ_FOREACH(header, req->output_headers, next) {
    528 		evbuffer_add_printf(evcon->output_buffer, "%s: %s\r\n",
    529 		    header->key, header->value);
    530 	}
    531 	evbuffer_add(evcon->output_buffer, "\r\n", 2);
    532 
    533 	if (EVBUFFER_LENGTH(req->output_buffer) > 0) {
    534 		/*
    535 		 * For a request, we add the POST data, for a reply, this
    536 		 * is the regular data.
    537 		 */
    538 		evbuffer_add_buffer(evcon->output_buffer, req->output_buffer);
    539 	}
    540 }
    541 
    542 /* Separated host, port and file from URI */
    543 
    544 int
    545 evhttp_hostportfile(char *url, char **phost, u_short *pport, char **pfile)
    546 {
    547 	/* XXX not threadsafe. */
    548 	static char host[1024];
    549 	static char file[1024];
    550 	char *p;
    551 	const char *p2;
    552 	int len;
    553 	u_short port;
    554 
    555 	len = strlen(HTTP_PREFIX);
    556 	if (strncasecmp(url, HTTP_PREFIX, len))
    557 		return (-1);
    558 
    559 	url += len;
    560 
    561 	/* We might overrun */
    562 	if (strlcpy(host, url, sizeof (host)) >= sizeof(host))
    563 		return (-1);
    564 
    565 	p = strchr(host, '/');
    566 	if (p != NULL) {
    567 		*p = '\0';
    568 		p2 = p + 1;
    569 	} else
    570 		p2 = NULL;
    571 
    572 	if (pfile != NULL) {
    573 		/* Generate request file */
    574 		if (p2 == NULL)
    575 			p2 = "";
    576 		evutil_snprintf(file, sizeof(file), "/%s", p2);
    577 	}
    578 
    579 	p = strchr(host, ':');
    580 	if (p != NULL) {
    581 		*p = '\0';
    582 		port = atoi(p + 1);
    583 
    584 		if (port == 0)
    585 			return (-1);
    586 	} else
    587 		port = HTTP_DEFAULTPORT;
    588 
    589 	if (phost != NULL)
    590 		*phost = host;
    591 	if (pport != NULL)
    592 		*pport = port;
    593 	if (pfile != NULL)
    594 		*pfile = file;
    595 
    596 	return (0);
    597 }
    598 
    599 static int
    600 evhttp_connection_incoming_fail(struct evhttp_request *req,
    601     enum evhttp_connection_error error)
    602 {
    603 	switch (error) {
    604 	case EVCON_HTTP_TIMEOUT:
    605 	case EVCON_HTTP_EOF:
    606 		/*
    607 		 * these are cases in which we probably should just
    608 		 * close the connection and not send a reply.  this
    609 		 * case may happen when a browser keeps a persistent
    610 		 * connection open and we timeout on the read.
    611 		 */
    612 		return (-1);
    613 	case EVCON_HTTP_INVALID_HEADER:
    614 	default:	/* xxx: probably should just error on default */
    615 		/* the callback looks at the uri to determine errors */
    616 		if (req->uri) {
    617 			free(req->uri);
    618 			req->uri = NULL;
    619 		}
    620 
    621 		/*
    622 		 * the callback needs to send a reply, once the reply has
    623 		 * been send, the connection should get freed.
    624 		 */
    625 		(*req->cb)(req, req->cb_arg);
    626 	}
    627 
    628 	return (0);
    629 }
    630 
    631 void
    632 evhttp_connection_fail(struct evhttp_connection *evcon,
    633     enum evhttp_connection_error error)
    634 {
    635 	struct evhttp_request* req = TAILQ_FIRST(&evcon->requests);
    636 	void (*cb)(struct evhttp_request *, void *);
    637 	void *cb_arg;
    638 	assert(req != NULL);
    639 
    640 	if (evcon->flags & EVHTTP_CON_INCOMING) {
    641 		/*
    642 		 * for incoming requests, there are two different
    643 		 * failure cases.  it's either a network level error
    644 		 * or an http layer error. for problems on the network
    645 		 * layer like timeouts we just drop the connections.
    646 		 * For HTTP problems, we might have to send back a
    647 		 * reply before the connection can be freed.
    648 		 */
    649 		if (evhttp_connection_incoming_fail(req, error) == -1)
    650 			evhttp_connection_free(evcon);
    651 		return;
    652 	}
    653 
    654 	/* save the callback for later; the cb might free our object */
    655 	cb = req->cb;
    656 	cb_arg = req->cb_arg;
    657 
    658 	TAILQ_REMOVE(&evcon->requests, req, next);
    659 	evhttp_request_free(req);
    660 
    661 	/* xxx: maybe we should fail all requests??? */
    662 
    663 	/* reset the connection */
    664 	evhttp_connection_reset(evcon);
    665 
    666 	/* We are trying the next request that was queued on us */
    667 	if (TAILQ_FIRST(&evcon->requests) != NULL)
    668 		evhttp_connection_connect(evcon);
    669 
    670 	/* inform the user */
    671 	if (cb != NULL)
    672 		(*cb)(NULL, cb_arg);
    673 }
    674 
    675 void
    676 evhttp_write(int fd, short what, void *arg)
    677 {
    678 	struct evhttp_connection *evcon = arg;
    679 	int n;
    680 
    681 	if (what == EV_TIMEOUT) {
    682 		evhttp_connection_fail(evcon, EVCON_HTTP_TIMEOUT);
    683 		return;
    684 	}
    685 
    686 	n = evbuffer_write(evcon->output_buffer, fd);
    687 	if (n == -1) {
    688 		event_debug(("%s: evbuffer_write", __func__));
    689 		evhttp_connection_fail(evcon, EVCON_HTTP_EOF);
    690 		return;
    691 	}
    692 
    693 	if (n == 0) {
    694 		event_debug(("%s: write nothing", __func__));
    695 		evhttp_connection_fail(evcon, EVCON_HTTP_EOF);
    696 		return;
    697 	}
    698 
    699 	if (EVBUFFER_LENGTH(evcon->output_buffer) != 0) {
    700 		evhttp_add_event(&evcon->ev,
    701 		    evcon->timeout, HTTP_WRITE_TIMEOUT);
    702 		return;
    703 	}
    704 
    705 	/* Activate our call back */
    706 	if (evcon->cb != NULL)
    707 		(*evcon->cb)(evcon, evcon->cb_arg);
    708 }
    709 
    710 /**
    711  * Advance the connection state.
    712  * - If this is an outgoing connection, we've just processed the response;
    713  *   idle or close the connection.
    714  * - If this is an incoming connection, we've just processed the request;
    715  *   respond.
    716  */
    717 static void
    718 evhttp_connection_done(struct evhttp_connection *evcon)
    719 {
    720 	struct evhttp_request *req = TAILQ_FIRST(&evcon->requests);
    721 	int con_outgoing = evcon->flags & EVHTTP_CON_OUTGOING;
    722 
    723 	if (con_outgoing) {
    724 		/* idle or close the connection */
    725 	        int need_close;
    726 		TAILQ_REMOVE(&evcon->requests, req, next);
    727 		req->evcon = NULL;
    728 
    729 		evcon->state = EVCON_IDLE;
    730 
    731 		need_close =
    732 		    evhttp_is_connection_close(req->flags, req->input_headers)||
    733 		    evhttp_is_connection_close(req->flags, req->output_headers);
    734 
    735 		/* check if we got asked to close the connection */
    736 		if (need_close)
    737 			evhttp_connection_reset(evcon);
    738 
    739 		if (TAILQ_FIRST(&evcon->requests) != NULL) {
    740 			/*
    741 			 * We have more requests; reset the connection
    742 			 * and deal with the next request.
    743 			 */
    744 			if (!evhttp_connected(evcon))
    745 				evhttp_connection_connect(evcon);
    746 			else
    747 				evhttp_request_dispatch(evcon);
    748 		} else if (!need_close) {
    749 			/*
    750 			 * The connection is going to be persistent, but we
    751 			 * need to detect if the other side closes it.
    752 			 */
    753 			evhttp_connection_start_detectclose(evcon);
    754 		}
    755 	} else {
    756 		/*
    757 		 * incoming connection - we need to leave the request on the
    758 		 * connection so that we can reply to it.
    759 		 */
    760 		evcon->state = EVCON_WRITING;
    761 	}
    762 
    763 	/* notify the user of the request */
    764 	(*req->cb)(req, req->cb_arg);
    765 
    766 	/* if this was an outgoing request, we own and it's done. so free it */
    767 	if (con_outgoing) {
    768 		evhttp_request_free(req);
    769 	}
    770 }
    771 
    772 /*
    773  * Handles reading from a chunked request.
    774  *   return ALL_DATA_READ:
    775  *     all data has been read
    776  *   return MORE_DATA_EXPECTED:
    777  *     more data is expected
    778  *   return DATA_CORRUPTED:
    779  *     data is corrupted
    780  *   return REQUEST_CANCLED:
    781  *     request was canceled by the user calling evhttp_cancel_request
    782  */
    783 
    784 static enum message_read_status
    785 evhttp_handle_chunked_read(struct evhttp_request *req, struct evbuffer *buf)
    786 {
    787 	int len;
    788 
    789 	while ((len = EVBUFFER_LENGTH(buf)) > 0) {
    790 		if (req->ntoread < 0) {
    791 			/* Read chunk size */
    792 			ev_int64_t ntoread;
    793 			char *p = evbuffer_readline(buf);
    794 			char *endp;
    795 			int error;
    796 			if (p == NULL)
    797 				break;
    798 			/* the last chunk is on a new line? */
    799 			if (strlen(p) == 0) {
    800 				free(p);
    801 				continue;
    802 			}
    803 			ntoread = evutil_strtoll(p, &endp, 16);
    804 			error = (*p == '\0' ||
    805 			    (*endp != '\0' && *endp != ' ') ||
    806 			    ntoread < 0);
    807 			free(p);
    808 			if (error) {
    809 				/* could not get chunk size */
    810 				return (DATA_CORRUPTED);
    811 			}
    812 			req->ntoread = ntoread;
    813 			if (req->ntoread == 0) {
    814 				/* Last chunk */
    815 				return (ALL_DATA_READ);
    816 			}
    817 			continue;
    818 		}
    819 
    820 		/* don't have enough to complete a chunk; wait for more */
    821 		if (len < req->ntoread)
    822 			return (MORE_DATA_EXPECTED);
    823 
    824 		/* Completed chunk */
    825 		evbuffer_add(req->input_buffer,
    826 		    EVBUFFER_DATA(buf), (size_t)req->ntoread);
    827 		evbuffer_drain(buf, (size_t)req->ntoread);
    828 		req->ntoread = -1;
    829 		if (req->chunk_cb != NULL) {
    830 			(*req->chunk_cb)(req, req->cb_arg);
    831 			evbuffer_drain(req->input_buffer,
    832 			    EVBUFFER_LENGTH(req->input_buffer));
    833 		}
    834 	}
    835 
    836 	return (MORE_DATA_EXPECTED);
    837 }
    838 
    839 static void
    840 evhttp_read_trailer(struct evhttp_connection *evcon, struct evhttp_request *req)
    841 {
    842 	struct evbuffer *buf = evcon->input_buffer;
    843 
    844 	switch (evhttp_parse_headers(req, buf)) {
    845 	case DATA_CORRUPTED:
    846 		evhttp_connection_fail(evcon, EVCON_HTTP_INVALID_HEADER);
    847 		break;
    848 	case ALL_DATA_READ:
    849 		event_del(&evcon->ev);
    850 		evhttp_connection_done(evcon);
    851 		break;
    852 	case MORE_DATA_EXPECTED:
    853 	default:
    854 		evhttp_add_event(&evcon->ev, evcon->timeout,
    855 		    HTTP_READ_TIMEOUT);
    856 		break;
    857 	}
    858 }
    859 
    860 static void
    861 evhttp_read_body(struct evhttp_connection *evcon, struct evhttp_request *req)
    862 {
    863 	struct evbuffer *buf = evcon->input_buffer;
    864 
    865 	if (req->chunked) {
    866 		switch (evhttp_handle_chunked_read(req, buf)) {
    867 		case ALL_DATA_READ:
    868 			/* finished last chunk */
    869 			evcon->state = EVCON_READING_TRAILER;
    870 			evhttp_read_trailer(evcon, req);
    871 			return;
    872 		case DATA_CORRUPTED:
    873 			/* corrupted data */
    874 			evhttp_connection_fail(evcon,
    875 			    EVCON_HTTP_INVALID_HEADER);
    876 			return;
    877 		case REQUEST_CANCELED:
    878 			/* request canceled */
    879 			evhttp_request_free(req);
    880 			return;
    881 		case MORE_DATA_EXPECTED:
    882 		default:
    883 			break;
    884 		}
    885 	} else if (req->ntoread < 0) {
    886 		/* Read until connection close. */
    887 		evbuffer_add_buffer(req->input_buffer, buf);
    888 	} else if (EVBUFFER_LENGTH(buf) >= req->ntoread) {
    889 		/* Completed content length */
    890 		evbuffer_add(req->input_buffer, EVBUFFER_DATA(buf),
    891 		    (size_t)req->ntoread);
    892 		evbuffer_drain(buf, (size_t)req->ntoread);
    893 		req->ntoread = 0;
    894 		evhttp_connection_done(evcon);
    895 		return;
    896 	}
    897 	/* Read more! */
    898 	event_set(&evcon->ev, evcon->fd, EV_READ, evhttp_read, evcon);
    899 	EVHTTP_BASE_SET(evcon, &evcon->ev);
    900 	evhttp_add_event(&evcon->ev, evcon->timeout, HTTP_READ_TIMEOUT);
    901 }
    902 
    903 /*
    904  * Reads data into a buffer structure until no more data
    905  * can be read on the file descriptor or we have read all
    906  * the data that we wanted to read.
    907  * Execute callback when done.
    908  */
    909 
    910 void
    911 evhttp_read(int fd, short what, void *arg)
    912 {
    913 	struct evhttp_connection *evcon = arg;
    914 	struct evhttp_request *req = TAILQ_FIRST(&evcon->requests);
    915 	struct evbuffer *buf = evcon->input_buffer;
    916 	int n, len;
    917 
    918 	if (what == EV_TIMEOUT) {
    919 		evhttp_connection_fail(evcon, EVCON_HTTP_TIMEOUT);
    920 		return;
    921 	}
    922 	n = evbuffer_read(buf, fd, -1);
    923 	len = EVBUFFER_LENGTH(buf);
    924 	event_debug(("%s: got %d on %d\n", __func__, n, fd));
    925 
    926 	if (n == -1) {
    927 		if (errno != EINTR && errno != EAGAIN) {
    928 			event_debug(("%s: evbuffer_read", __func__));
    929 			evhttp_connection_fail(evcon, EVCON_HTTP_EOF);
    930 		} else {
    931 			evhttp_add_event(&evcon->ev, evcon->timeout,
    932 			    HTTP_READ_TIMEOUT);
    933 		}
    934 		return;
    935 	} else if (n == 0) {
    936 		/* Connection closed */
    937 		evhttp_connection_done(evcon);
    938 		return;
    939 	}
    940 
    941 	switch (evcon->state) {
    942 	case EVCON_READING_FIRSTLINE:
    943 		evhttp_read_firstline(evcon, req);
    944 		break;
    945 	case EVCON_READING_HEADERS:
    946 		evhttp_read_header(evcon, req);
    947 		break;
    948 	case EVCON_READING_BODY:
    949 		evhttp_read_body(evcon, req);
    950 		break;
    951 	case EVCON_READING_TRAILER:
    952 		evhttp_read_trailer(evcon, req);
    953 		break;
    954 	case EVCON_DISCONNECTED:
    955 	case EVCON_CONNECTING:
    956 	case EVCON_IDLE:
    957 	case EVCON_WRITING:
    958 	default:
    959 		event_errx(1, "%s: illegal connection state %d",
    960 			   __func__, evcon->state);
    961 	}
    962 }
    963 
    964 static void
    965 evhttp_write_connectioncb(struct evhttp_connection *evcon, void *arg)
    966 {
    967 	/* This is after writing the request to the server */
    968 	struct evhttp_request *req = TAILQ_FIRST(&evcon->requests);
    969 	assert(req != NULL);
    970 
    971 	assert(evcon->state == EVCON_WRITING);
    972 
    973 	/* We are done writing our header and are now expecting the response */
    974 	req->kind = EVHTTP_RESPONSE;
    975 
    976 	evhttp_start_read(evcon);
    977 }
    978 
    979 /*
    980  * Clean up a connection object
    981  */
    982 
    983 void
    984 evhttp_connection_free(struct evhttp_connection *evcon)
    985 {
    986 	struct evhttp_request *req;
    987 
    988 	/* notify interested parties that this connection is going down */
    989 	if (evcon->fd != -1) {
    990 		if (evhttp_connected(evcon) && evcon->closecb != NULL)
    991 			(*evcon->closecb)(evcon, evcon->closecb_arg);
    992 	}
    993 
    994 	/* remove all requests that might be queued on this connection */
    995 	while ((req = TAILQ_FIRST(&evcon->requests)) != NULL) {
    996 		TAILQ_REMOVE(&evcon->requests, req, next);
    997 		evhttp_request_free(req);
    998 	}
    999 
   1000 	if (evcon->http_server != NULL) {
   1001 		struct evhttp *http = evcon->http_server;
   1002 		TAILQ_REMOVE(&http->connections, evcon, next);
   1003 	}
   1004 
   1005 	if (event_initialized(&evcon->close_ev))
   1006 		event_del(&evcon->close_ev);
   1007 
   1008 	if (event_initialized(&evcon->ev))
   1009 		event_del(&evcon->ev);
   1010 
   1011 	if (evcon->fd != -1)
   1012 		EVUTIL_CLOSESOCKET(evcon->fd);
   1013 
   1014 	if (evcon->bind_address != NULL)
   1015 		free(evcon->bind_address);
   1016 
   1017 	if (evcon->address != NULL)
   1018 		free(evcon->address);
   1019 
   1020 	if (evcon->input_buffer != NULL)
   1021 		evbuffer_free(evcon->input_buffer);
   1022 
   1023 	if (evcon->output_buffer != NULL)
   1024 		evbuffer_free(evcon->output_buffer);
   1025 
   1026 	free(evcon);
   1027 }
   1028 
   1029 void
   1030 evhttp_connection_set_local_address(struct evhttp_connection *evcon,
   1031     const char *address)
   1032 {
   1033 	assert(evcon->state == EVCON_DISCONNECTED);
   1034 	if (evcon->bind_address)
   1035 		free(evcon->bind_address);
   1036 	if ((evcon->bind_address = strdup(address)) == NULL)
   1037 		event_err(1, "%s: strdup", __func__);
   1038 }
   1039 
   1040 void
   1041 evhttp_connection_set_local_port(struct evhttp_connection *evcon,
   1042     unsigned short port)
   1043 {
   1044 	assert(evcon->state == EVCON_DISCONNECTED);
   1045 	evcon->bind_port = port;
   1046 }
   1047 
   1048 static void
   1049 evhttp_request_dispatch(struct evhttp_connection* evcon)
   1050 {
   1051 	struct evhttp_request *req = TAILQ_FIRST(&evcon->requests);
   1052 
   1053 	/* this should not usually happy but it's possible */
   1054 	if (req == NULL)
   1055 		return;
   1056 
   1057 	/* delete possible close detection events */
   1058 	evhttp_connection_stop_detectclose(evcon);
   1059 
   1060 	/* we assume that the connection is connected already */
   1061 	assert(evcon->state == EVCON_IDLE);
   1062 
   1063 	evcon->state = EVCON_WRITING;
   1064 
   1065 	/* Create the header from the store arguments */
   1066 	evhttp_make_header(evcon, req);
   1067 
   1068 	evhttp_write_buffer(evcon, evhttp_write_connectioncb, NULL);
   1069 }
   1070 
   1071 /* Reset our connection state */
   1072 void
   1073 evhttp_connection_reset(struct evhttp_connection *evcon)
   1074 {
   1075 	if (event_initialized(&evcon->ev))
   1076 		event_del(&evcon->ev);
   1077 
   1078 	if (evcon->fd != -1) {
   1079 		/* inform interested parties about connection close */
   1080 		if (evhttp_connected(evcon) && evcon->closecb != NULL)
   1081 			(*evcon->closecb)(evcon, evcon->closecb_arg);
   1082 
   1083 		EVUTIL_CLOSESOCKET(evcon->fd);
   1084 		evcon->fd = -1;
   1085 	}
   1086 	evcon->state = EVCON_DISCONNECTED;
   1087 
   1088 	evbuffer_drain(evcon->input_buffer,
   1089 	    EVBUFFER_LENGTH(evcon->input_buffer));
   1090 	evbuffer_drain(evcon->output_buffer,
   1091 	    EVBUFFER_LENGTH(evcon->output_buffer));
   1092 }
   1093 
   1094 static void
   1095 evhttp_detect_close_cb(int fd, short what, void *arg)
   1096 {
   1097 	struct evhttp_connection *evcon = arg;
   1098 	evhttp_connection_reset(evcon);
   1099 }
   1100 
   1101 static void
   1102 evhttp_connection_start_detectclose(struct evhttp_connection *evcon)
   1103 {
   1104 	evcon->flags |= EVHTTP_CON_CLOSEDETECT;
   1105 
   1106 	if (event_initialized(&evcon->close_ev))
   1107 		event_del(&evcon->close_ev);
   1108 	event_set(&evcon->close_ev, evcon->fd, EV_READ,
   1109 	    evhttp_detect_close_cb, evcon);
   1110 	EVHTTP_BASE_SET(evcon, &evcon->close_ev);
   1111 	event_add(&evcon->close_ev, NULL);
   1112 }
   1113 
   1114 static void
   1115 evhttp_connection_stop_detectclose(struct evhttp_connection *evcon)
   1116 {
   1117 	evcon->flags &= ~EVHTTP_CON_CLOSEDETECT;
   1118 	event_del(&evcon->close_ev);
   1119 }
   1120 
   1121 static void
   1122 evhttp_connection_retry(int fd, short what, void *arg)
   1123 {
   1124 	struct evhttp_connection *evcon = arg;
   1125 
   1126 	evcon->state = EVCON_DISCONNECTED;
   1127 	evhttp_connection_connect(evcon);
   1128 }
   1129 
   1130 /*
   1131  * Call back for asynchronous connection attempt.
   1132  */
   1133 
   1134 static void
   1135 evhttp_connectioncb(int fd, short what, void *arg)
   1136 {
   1137 	struct evhttp_connection *evcon = arg;
   1138 	int error;
   1139 	socklen_t errsz = sizeof(error);
   1140 
   1141 	if (what == EV_TIMEOUT) {
   1142 		event_debug(("%s: connection timeout for \"%s:%d\" on %d",
   1143 			__func__, evcon->address, evcon->port, evcon->fd));
   1144 		goto cleanup;
   1145 	}
   1146 
   1147 	/* Check if the connection completed */
   1148 	if (getsockopt(evcon->fd, SOL_SOCKET, SO_ERROR, (void*)&error,
   1149 		       &errsz) == -1) {
   1150 		event_debug(("%s: getsockopt for \"%s:%d\" on %d",
   1151 			__func__, evcon->address, evcon->port, evcon->fd));
   1152 		goto cleanup;
   1153 	}
   1154 
   1155 	if (error) {
   1156 		event_debug(("%s: connect failed for \"%s:%d\" on %d: %s",
   1157 		    __func__, evcon->address, evcon->port, evcon->fd,
   1158 			strerror(error)));
   1159 		goto cleanup;
   1160 	}
   1161 
   1162 	/* We are connected to the server now */
   1163 	event_debug(("%s: connected to \"%s:%d\" on %d\n",
   1164 			__func__, evcon->address, evcon->port, evcon->fd));
   1165 
   1166 	/* Reset the retry count as we were successful in connecting */
   1167 	evcon->retry_cnt = 0;
   1168 	evcon->state = EVCON_IDLE;
   1169 
   1170 	/* try to start requests that have queued up on this connection */
   1171 	evhttp_request_dispatch(evcon);
   1172 	return;
   1173 
   1174  cleanup:
   1175 	if (evcon->retry_max < 0 || evcon->retry_cnt < evcon->retry_max) {
   1176 		evtimer_set(&evcon->ev, evhttp_connection_retry, evcon);
   1177 		EVHTTP_BASE_SET(evcon, &evcon->ev);
   1178 		evhttp_add_event(&evcon->ev, MIN(3600, 2 << evcon->retry_cnt),
   1179 		    HTTP_CONNECT_TIMEOUT);
   1180 		evcon->retry_cnt++;
   1181 		return;
   1182 	}
   1183 	evhttp_connection_reset(evcon);
   1184 
   1185 	/* for now, we just signal all requests by executing their callbacks */
   1186 	while (TAILQ_FIRST(&evcon->requests) != NULL) {
   1187 		struct evhttp_request *request = TAILQ_FIRST(&evcon->requests);
   1188 		TAILQ_REMOVE(&evcon->requests, request, next);
   1189 		request->evcon = NULL;
   1190 
   1191 		/* we might want to set an error here */
   1192 		request->cb(request, request->cb_arg);
   1193 		evhttp_request_free(request);
   1194 	}
   1195 }
   1196 
   1197 /*
   1198  * Check if we got a valid response code.
   1199  */
   1200 
   1201 static int
   1202 evhttp_valid_response_code(int code)
   1203 {
   1204 	if (code == 0)
   1205 		return (0);
   1206 
   1207 	return (1);
   1208 }
   1209 
   1210 /* Parses the status line of a web server */
   1211 
   1212 static int
   1213 evhttp_parse_response_line(struct evhttp_request *req, char *line)
   1214 {
   1215 	char *protocol;
   1216 	char *number;
   1217 	char *readable;
   1218 
   1219 	protocol = strsep(&line, " ");
   1220 	if (line == NULL)
   1221 		return (-1);
   1222 	number = strsep(&line, " ");
   1223 	if (line == NULL)
   1224 		return (-1);
   1225 	readable = line;
   1226 
   1227 	if (strcmp(protocol, "HTTP/1.0") == 0) {
   1228 		req->major = 1;
   1229 		req->minor = 0;
   1230 	} else if (strcmp(protocol, "HTTP/1.1") == 0) {
   1231 		req->major = 1;
   1232 		req->minor = 1;
   1233 	} else {
   1234 		event_debug(("%s: bad protocol \"%s\"",
   1235 			__func__, protocol));
   1236 		return (-1);
   1237 	}
   1238 
   1239 	req->response_code = atoi(number);
   1240 	if (!evhttp_valid_response_code(req->response_code)) {
   1241 		event_debug(("%s: bad response code \"%s\"",
   1242 			__func__, number));
   1243 		return (-1);
   1244 	}
   1245 
   1246 	if ((req->response_code_line = strdup(readable)) == NULL)
   1247 		event_err(1, "%s: strdup", __func__);
   1248 
   1249 	return (0);
   1250 }
   1251 
   1252 /* Parse the first line of a HTTP request */
   1253 
   1254 static int
   1255 evhttp_parse_request_line(struct evhttp_request *req, char *line)
   1256 {
   1257 	char *method;
   1258 	char *uri;
   1259 	char *version;
   1260 
   1261 	/* Parse the request line */
   1262 	method = strsep(&line, " ");
   1263 	if (line == NULL)
   1264 		return (-1);
   1265 	uri = strsep(&line, " ");
   1266 	if (line == NULL)
   1267 		return (-1);
   1268 	version = strsep(&line, " ");
   1269 	if (line != NULL)
   1270 		return (-1);
   1271 
   1272 	/* First line */
   1273 	if (strcmp(method, "GET") == 0) {
   1274 		req->type = EVHTTP_REQ_GET;
   1275 	} else if (strcmp(method, "POST") == 0) {
   1276 		req->type = EVHTTP_REQ_POST;
   1277 	} else if (strcmp(method, "HEAD") == 0) {
   1278 		req->type = EVHTTP_REQ_HEAD;
   1279 	} else {
   1280 		event_debug(("%s: bad method %s on request %p from %s",
   1281 			__func__, method, req, req->remote_host));
   1282 		return (-1);
   1283 	}
   1284 
   1285 	if (strcmp(version, "HTTP/1.0") == 0) {
   1286 		req->major = 1;
   1287 		req->minor = 0;
   1288 	} else if (strcmp(version, "HTTP/1.1") == 0) {
   1289 		req->major = 1;
   1290 		req->minor = 1;
   1291 	} else {
   1292 		event_debug(("%s: bad version %s on request %p from %s",
   1293 			__func__, version, req, req->remote_host));
   1294 		return (-1);
   1295 	}
   1296 
   1297 	if ((req->uri = strdup(uri)) == NULL) {
   1298 		event_debug(("%s: evhttp_decode_uri", __func__));
   1299 		return (-1);
   1300 	}
   1301 
   1302 	/* determine if it's a proxy request */
   1303 	if (strlen(req->uri) > 0 && req->uri[0] != '/')
   1304 		req->flags |= EVHTTP_PROXY_REQUEST;
   1305 
   1306 	return (0);
   1307 }
   1308 
   1309 const char *
   1310 evhttp_find_header(const struct evkeyvalq *headers, const char *key)
   1311 {
   1312 	struct evkeyval *header;
   1313 
   1314 	TAILQ_FOREACH(header, headers, next) {
   1315 		if (strcasecmp(header->key, key) == 0)
   1316 			return (header->value);
   1317 	}
   1318 
   1319 	return (NULL);
   1320 }
   1321 
   1322 void
   1323 evhttp_clear_headers(struct evkeyvalq *headers)
   1324 {
   1325 	struct evkeyval *header;
   1326 
   1327 	for (header = TAILQ_FIRST(headers);
   1328 	    header != NULL;
   1329 	    header = TAILQ_FIRST(headers)) {
   1330 		TAILQ_REMOVE(headers, header, next);
   1331 		free(header->key);
   1332 		free(header->value);
   1333 		free(header);
   1334 	}
   1335 }
   1336 
   1337 /*
   1338  * Returns 0,  if the header was successfully removed.
   1339  * Returns -1, if the header could not be found.
   1340  */
   1341 
   1342 int
   1343 evhttp_remove_header(struct evkeyvalq *headers, const char *key)
   1344 {
   1345 	struct evkeyval *header;
   1346 
   1347 	TAILQ_FOREACH(header, headers, next) {
   1348 		if (strcasecmp(header->key, key) == 0)
   1349 			break;
   1350 	}
   1351 
   1352 	if (header == NULL)
   1353 		return (-1);
   1354 
   1355 	/* Free and remove the header that we found */
   1356 	TAILQ_REMOVE(headers, header, next);
   1357 	free(header->key);
   1358 	free(header->value);
   1359 	free(header);
   1360 
   1361 	return (0);
   1362 }
   1363 
   1364 static int
   1365 evhttp_header_is_valid_value(const char *value)
   1366 {
   1367 	const char *p = value;
   1368 
   1369 	while ((p = strpbrk(p, "\r\n")) != NULL) {
   1370 		/* we really expect only one new line */
   1371 		p += strspn(p, "\r\n");
   1372 		/* we expect a space or tab for continuation */
   1373 		if (*p != ' ' && *p != '\t')
   1374 			return (0);
   1375 	}
   1376 	return (1);
   1377 }
   1378 
   1379 int
   1380 evhttp_add_header(struct evkeyvalq *headers,
   1381     const char *key, const char *value)
   1382 {
   1383 	event_debug(("%s: key: %s val: %s\n", __func__, key, value));
   1384 
   1385 	if (strchr(key, '\r') != NULL || strchr(key, '\n') != NULL) {
   1386 		/* drop illegal headers */
   1387 		event_debug(("%s: dropping illegal header key\n", __func__));
   1388 		return (-1);
   1389 	}
   1390 
   1391 	if (!evhttp_header_is_valid_value(value)) {
   1392 		event_debug(("%s: dropping illegal header value\n", __func__));
   1393 		return (-1);
   1394 	}
   1395 
   1396 	return (evhttp_add_header_internal(headers, key, value));
   1397 }
   1398 
   1399 static int
   1400 evhttp_add_header_internal(struct evkeyvalq *headers,
   1401     const char *key, const char *value)
   1402 {
   1403 	struct evkeyval *header = calloc(1, sizeof(struct evkeyval));
   1404 	if (header == NULL) {
   1405 		event_warn("%s: calloc", __func__);
   1406 		return (-1);
   1407 	}
   1408 	if ((header->key = strdup(key)) == NULL) {
   1409 		free(header);
   1410 		event_warn("%s: strdup", __func__);
   1411 		return (-1);
   1412 	}
   1413 	if ((header->value = strdup(value)) == NULL) {
   1414 		free(header->key);
   1415 		free(header);
   1416 		event_warn("%s: strdup", __func__);
   1417 		return (-1);
   1418 	}
   1419 
   1420 	TAILQ_INSERT_TAIL(headers, header, next);
   1421 
   1422 	return (0);
   1423 }
   1424 
   1425 /*
   1426  * Parses header lines from a request or a response into the specified
   1427  * request object given an event buffer.
   1428  *
   1429  * Returns
   1430  *   DATA_CORRUPTED      on error
   1431  *   MORE_DATA_EXPECTED  when we need to read more headers
   1432  *   ALL_DATA_READ       when all headers have been read.
   1433  */
   1434 
   1435 enum message_read_status
   1436 evhttp_parse_firstline(struct evhttp_request *req, struct evbuffer *buffer)
   1437 {
   1438 	char *line;
   1439 	enum message_read_status status = ALL_DATA_READ;
   1440 
   1441 	line = evbuffer_readline(buffer);
   1442 	if (line == NULL)
   1443 		return (MORE_DATA_EXPECTED);
   1444 
   1445 	switch (req->kind) {
   1446 	case EVHTTP_REQUEST:
   1447 		if (evhttp_parse_request_line(req, line) == -1)
   1448 			status = DATA_CORRUPTED;
   1449 		break;
   1450 	case EVHTTP_RESPONSE:
   1451 		if (evhttp_parse_response_line(req, line) == -1)
   1452 			status = DATA_CORRUPTED;
   1453 		break;
   1454 	default:
   1455 		status = DATA_CORRUPTED;
   1456 	}
   1457 
   1458 	free(line);
   1459 	return (status);
   1460 }
   1461 
   1462 static int
   1463 evhttp_append_to_last_header(struct evkeyvalq *headers, const char *line)
   1464 {
   1465 	struct evkeyval *header = TAILQ_LAST(headers, evkeyvalq);
   1466 	char *newval;
   1467 	size_t old_len, line_len;
   1468 
   1469 	if (header == NULL)
   1470 		return (-1);
   1471 
   1472 	old_len = strlen(header->value);
   1473 	line_len = strlen(line);
   1474 
   1475 	newval = realloc(header->value, old_len + line_len + 1);
   1476 	if (newval == NULL)
   1477 		return (-1);
   1478 
   1479 	memcpy(newval + old_len, line, line_len + 1);
   1480 	header->value = newval;
   1481 
   1482 	return (0);
   1483 }
   1484 
   1485 enum message_read_status
   1486 evhttp_parse_headers(struct evhttp_request *req, struct evbuffer* buffer)
   1487 {
   1488 	char *line;
   1489 	enum message_read_status status = MORE_DATA_EXPECTED;
   1490 
   1491 	struct evkeyvalq* headers = req->input_headers;
   1492 	while ((line = evbuffer_readline(buffer))
   1493 	       != NULL) {
   1494 		char *skey, *svalue;
   1495 
   1496 		if (*line == '\0') { /* Last header - Done */
   1497 			status = ALL_DATA_READ;
   1498 			free(line);
   1499 			break;
   1500 		}
   1501 
   1502 		/* Check if this is a continuation line */
   1503 		if (*line == ' ' || *line == '\t') {
   1504 			if (evhttp_append_to_last_header(headers, line) == -1)
   1505 				goto error;
   1506 			free(line);
   1507 			continue;
   1508 		}
   1509 
   1510 		/* Processing of header lines */
   1511 		svalue = line;
   1512 		skey = strsep(&svalue, ":");
   1513 		if (svalue == NULL)
   1514 			goto error;
   1515 
   1516 		svalue += strspn(svalue, " ");
   1517 
   1518 		if (evhttp_add_header(headers, skey, svalue) == -1)
   1519 			goto error;
   1520 
   1521 		free(line);
   1522 	}
   1523 
   1524 	return (status);
   1525 
   1526  error:
   1527 	free(line);
   1528 	return (DATA_CORRUPTED);
   1529 }
   1530 
   1531 static int
   1532 evhttp_get_body_length(struct evhttp_request *req)
   1533 {
   1534 	struct evkeyvalq *headers = req->input_headers;
   1535 	const char *content_length;
   1536 	const char *connection;
   1537 
   1538 	content_length = evhttp_find_header(headers, "Content-Length");
   1539 	connection = evhttp_find_header(headers, "Connection");
   1540 
   1541 	if (content_length == NULL && connection == NULL)
   1542 		req->ntoread = -1;
   1543 	else if (content_length == NULL &&
   1544 	    strcasecmp(connection, "Close") != 0) {
   1545 		/* Bad combination, we don't know when it will end */
   1546 		event_warnx("%s: we got no content length, but the "
   1547 		    "server wants to keep the connection open: %s.",
   1548 		    __func__, connection);
   1549 		return (-1);
   1550 	} else if (content_length == NULL) {
   1551 		req->ntoread = -1;
   1552 	} else {
   1553 		char *endp;
   1554 		ev_int64_t ntoread = evutil_strtoll(content_length, &endp, 10);
   1555 		if (*content_length == '\0' || *endp != '\0' || ntoread < 0) {
   1556 			event_debug(("%s: illegal content length: %s",
   1557 				__func__, content_length));
   1558 			return (-1);
   1559 		}
   1560 		req->ntoread = ntoread;
   1561 	}
   1562 
   1563 	event_debug(("%s: bytes to read: %lld (in buffer %ld)\n",
   1564 		__func__, req->ntoread,
   1565 		EVBUFFER_LENGTH(req->evcon->input_buffer)));
   1566 
   1567 	return (0);
   1568 }
   1569 
   1570 static void
   1571 evhttp_get_body(struct evhttp_connection *evcon, struct evhttp_request *req)
   1572 {
   1573 	const char *xfer_enc;
   1574 
   1575 	/* If this is a request without a body, then we are done */
   1576 	if (req->kind == EVHTTP_REQUEST && req->type != EVHTTP_REQ_POST) {
   1577 		evhttp_connection_done(evcon);
   1578 		return;
   1579 	}
   1580 	evcon->state = EVCON_READING_BODY;
   1581 	xfer_enc = evhttp_find_header(req->input_headers, "Transfer-Encoding");
   1582 	if (xfer_enc != NULL && strcasecmp(xfer_enc, "chunked") == 0) {
   1583 		req->chunked = 1;
   1584 		req->ntoread = -1;
   1585 	} else {
   1586 		if (evhttp_get_body_length(req) == -1) {
   1587 			evhttp_connection_fail(evcon,
   1588 			    EVCON_HTTP_INVALID_HEADER);
   1589 			return;
   1590 		}
   1591 	}
   1592 	evhttp_read_body(evcon, req);
   1593 }
   1594 
   1595 static void
   1596 evhttp_read_firstline(struct evhttp_connection *evcon,
   1597 		      struct evhttp_request *req)
   1598 {
   1599 	enum message_read_status res;
   1600 
   1601 	res = evhttp_parse_firstline(req, evcon->input_buffer);
   1602 	if (res == DATA_CORRUPTED) {
   1603 		/* Error while reading, terminate */
   1604 		event_debug(("%s: bad header lines on %d\n",
   1605 			__func__, evcon->fd));
   1606 		evhttp_connection_fail(evcon, EVCON_HTTP_INVALID_HEADER);
   1607 		return;
   1608 	} else if (res == MORE_DATA_EXPECTED) {
   1609 		/* Need more header lines */
   1610 		evhttp_add_event(&evcon->ev,
   1611                     evcon->timeout, HTTP_READ_TIMEOUT);
   1612 		return;
   1613 	}
   1614 
   1615 	evcon->state = EVCON_READING_HEADERS;
   1616 	evhttp_read_header(evcon, req);
   1617 }
   1618 
   1619 static void
   1620 evhttp_read_header(struct evhttp_connection *evcon, struct evhttp_request *req)
   1621 {
   1622 	enum message_read_status res;
   1623 	int fd = evcon->fd;
   1624 
   1625 	res = evhttp_parse_headers(req, evcon->input_buffer);
   1626 	if (res == DATA_CORRUPTED) {
   1627 		/* Error while reading, terminate */
   1628 		event_debug(("%s: bad header lines on %d\n", __func__, fd));
   1629 		evhttp_connection_fail(evcon, EVCON_HTTP_INVALID_HEADER);
   1630 		return;
   1631 	} else if (res == MORE_DATA_EXPECTED) {
   1632 		/* Need more header lines */
   1633 		evhttp_add_event(&evcon->ev,
   1634 		    evcon->timeout, HTTP_READ_TIMEOUT);
   1635 		return;
   1636 	}
   1637 
   1638 	/* Done reading headers, do the real work */
   1639 	switch (req->kind) {
   1640 	case EVHTTP_REQUEST:
   1641 		event_debug(("%s: checking for post data on %d\n",
   1642 				__func__, fd));
   1643 		evhttp_get_body(evcon, req);
   1644 		break;
   1645 
   1646 	case EVHTTP_RESPONSE:
   1647 		if (req->response_code == HTTP_NOCONTENT ||
   1648 		    req->response_code == HTTP_NOTMODIFIED ||
   1649 		    (req->response_code >= 100 && req->response_code < 200)) {
   1650 			event_debug(("%s: skipping body for code %d\n",
   1651 					__func__, req->response_code));
   1652 			evhttp_connection_done(evcon);
   1653 		} else {
   1654 			event_debug(("%s: start of read body for %s on %d\n",
   1655 				__func__, req->remote_host, fd));
   1656 			evhttp_get_body(evcon, req);
   1657 		}
   1658 		break;
   1659 
   1660 	default:
   1661 		event_warnx("%s: bad header on %d", __func__, fd);
   1662 		evhttp_connection_fail(evcon, EVCON_HTTP_INVALID_HEADER);
   1663 		break;
   1664 	}
   1665 }
   1666 
   1667 /*
   1668  * Creates a TCP connection to the specified port and executes a callback
   1669  * when finished.  Failure or sucess is indicate by the passed connection
   1670  * object.
   1671  *
   1672  * Although this interface accepts a hostname, it is intended to take
   1673  * only numeric hostnames so that non-blocking DNS resolution can
   1674  * happen elsewhere.
   1675  */
   1676 
   1677 struct evhttp_connection *
   1678 evhttp_connection_new(const char *address, unsigned short port)
   1679 {
   1680 	struct evhttp_connection *evcon = NULL;
   1681 
   1682 	event_debug(("Attempting connection to %s:%d\n", address, port));
   1683 
   1684 	if ((evcon = calloc(1, sizeof(struct evhttp_connection))) == NULL) {
   1685 		event_warn("%s: calloc failed", __func__);
   1686 		goto error;
   1687 	}
   1688 
   1689 	evcon->fd = -1;
   1690 	evcon->port = port;
   1691 
   1692 	evcon->timeout = -1;
   1693 	evcon->retry_cnt = evcon->retry_max = 0;
   1694 
   1695 	if ((evcon->address = strdup(address)) == NULL) {
   1696 		event_warn("%s: strdup failed", __func__);
   1697 		goto error;
   1698 	}
   1699 
   1700 	if ((evcon->input_buffer = evbuffer_new()) == NULL) {
   1701 		event_warn("%s: evbuffer_new failed", __func__);
   1702 		goto error;
   1703 	}
   1704 
   1705 	if ((evcon->output_buffer = evbuffer_new()) == NULL) {
   1706 		event_warn("%s: evbuffer_new failed", __func__);
   1707 		goto error;
   1708 	}
   1709 
   1710 	evcon->state = EVCON_DISCONNECTED;
   1711 	TAILQ_INIT(&evcon->requests);
   1712 
   1713 	return (evcon);
   1714 
   1715  error:
   1716 	if (evcon != NULL)
   1717 		evhttp_connection_free(evcon);
   1718 	return (NULL);
   1719 }
   1720 
   1721 void evhttp_connection_set_base(struct evhttp_connection *evcon,
   1722     struct event_base *base)
   1723 {
   1724 	assert(evcon->base == NULL);
   1725 	assert(evcon->state == EVCON_DISCONNECTED);
   1726 	evcon->base = base;
   1727 }
   1728 
   1729 void
   1730 evhttp_connection_set_timeout(struct evhttp_connection *evcon,
   1731     int timeout_in_secs)
   1732 {
   1733 	evcon->timeout = timeout_in_secs;
   1734 }
   1735 
   1736 void
   1737 evhttp_connection_set_retries(struct evhttp_connection *evcon,
   1738     int retry_max)
   1739 {
   1740 	evcon->retry_max = retry_max;
   1741 }
   1742 
   1743 void
   1744 evhttp_connection_set_closecb(struct evhttp_connection *evcon,
   1745     void (*cb)(struct evhttp_connection *, void *), void *cbarg)
   1746 {
   1747 	evcon->closecb = cb;
   1748 	evcon->closecb_arg = cbarg;
   1749 }
   1750 
   1751 void
   1752 evhttp_connection_get_peer(struct evhttp_connection *evcon,
   1753     char **address, u_short *port)
   1754 {
   1755 	*address = evcon->address;
   1756 	*port = evcon->port;
   1757 }
   1758 
   1759 int
   1760 evhttp_connection_connect(struct evhttp_connection *evcon)
   1761 {
   1762 	if (evcon->state == EVCON_CONNECTING)
   1763 		return (0);
   1764 
   1765 	evhttp_connection_reset(evcon);
   1766 
   1767 	assert(!(evcon->flags & EVHTTP_CON_INCOMING));
   1768 	evcon->flags |= EVHTTP_CON_OUTGOING;
   1769 
   1770 	evcon->fd = bind_socket(
   1771 		evcon->bind_address, evcon->bind_port, 0 /*reuse*/);
   1772 	if (evcon->fd == -1) {
   1773 		event_debug(("%s: failed to bind to \"%s\"",
   1774 			__func__, evcon->bind_address));
   1775 		return (-1);
   1776 	}
   1777 
   1778 	if (socket_connect(evcon->fd, evcon->address, evcon->port) == -1) {
   1779 		EVUTIL_CLOSESOCKET(evcon->fd); evcon->fd = -1;
   1780 		return (-1);
   1781 	}
   1782 
   1783 	/* Set up a callback for successful connection setup */
   1784 	event_set(&evcon->ev, evcon->fd, EV_WRITE, evhttp_connectioncb, evcon);
   1785 	EVHTTP_BASE_SET(evcon, &evcon->ev);
   1786 	evhttp_add_event(&evcon->ev, evcon->timeout, HTTP_CONNECT_TIMEOUT);
   1787 
   1788 	evcon->state = EVCON_CONNECTING;
   1789 
   1790 	return (0);
   1791 }
   1792 
   1793 /*
   1794  * Starts an HTTP request on the provided evhttp_connection object.
   1795  * If the connection object is not connected to the web server already,
   1796  * this will start the connection.
   1797  */
   1798 
   1799 int
   1800 evhttp_make_request(struct evhttp_connection *evcon,
   1801     struct evhttp_request *req,
   1802     enum evhttp_cmd_type type, const char *uri)
   1803 {
   1804 	/* We are making a request */
   1805 	req->kind = EVHTTP_REQUEST;
   1806 	req->type = type;
   1807 	if (req->uri != NULL)
   1808 		free(req->uri);
   1809 	if ((req->uri = strdup(uri)) == NULL)
   1810 		event_err(1, "%s: strdup", __func__);
   1811 
   1812 	/* Set the protocol version if it is not supplied */
   1813 	if (!req->major && !req->minor) {
   1814 		req->major = 1;
   1815 		req->minor = 1;
   1816 	}
   1817 
   1818 	assert(req->evcon == NULL);
   1819 	req->evcon = evcon;
   1820 	assert(!(req->flags & EVHTTP_REQ_OWN_CONNECTION));
   1821 
   1822 	TAILQ_INSERT_TAIL(&evcon->requests, req, next);
   1823 
   1824 	/* If the connection object is not connected; make it so */
   1825 	if (!evhttp_connected(evcon))
   1826 		return (evhttp_connection_connect(evcon));
   1827 
   1828 	/*
   1829 	 * If it's connected already and we are the first in the queue,
   1830 	 * then we can dispatch this request immediately.  Otherwise, it
   1831 	 * will be dispatched once the pending requests are completed.
   1832 	 */
   1833 	if (TAILQ_FIRST(&evcon->requests) == req)
   1834 		evhttp_request_dispatch(evcon);
   1835 
   1836 	return (0);
   1837 }
   1838 
   1839 /*
   1840  * Reads data from file descriptor into request structure
   1841  * Request structure needs to be set up correctly.
   1842  */
   1843 
   1844 void
   1845 evhttp_start_read(struct evhttp_connection *evcon)
   1846 {
   1847 	/* Set up an event to read the headers */
   1848 	if (event_initialized(&evcon->ev))
   1849 		event_del(&evcon->ev);
   1850 	event_set(&evcon->ev, evcon->fd, EV_READ, evhttp_read, evcon);
   1851 	EVHTTP_BASE_SET(evcon, &evcon->ev);
   1852 
   1853 	evhttp_add_event(&evcon->ev, evcon->timeout, HTTP_READ_TIMEOUT);
   1854 	evcon->state = EVCON_READING_FIRSTLINE;
   1855 }
   1856 
   1857 static void
   1858 evhttp_send_done(struct evhttp_connection *evcon, void *arg)
   1859 {
   1860 	int need_close;
   1861 	struct evhttp_request *req = TAILQ_FIRST(&evcon->requests);
   1862 	TAILQ_REMOVE(&evcon->requests, req, next);
   1863 
   1864 	/* delete possible close detection events */
   1865 	evhttp_connection_stop_detectclose(evcon);
   1866 
   1867 	need_close =
   1868 	    (req->minor == 0 &&
   1869 		!evhttp_is_connection_keepalive(req->input_headers))||
   1870 	    evhttp_is_connection_close(req->flags, req->input_headers) ||
   1871 	    evhttp_is_connection_close(req->flags, req->output_headers);
   1872 
   1873 	assert(req->flags & EVHTTP_REQ_OWN_CONNECTION);
   1874 	evhttp_request_free(req);
   1875 
   1876 	if (need_close) {
   1877 		evhttp_connection_free(evcon);
   1878 		return;
   1879 	}
   1880 
   1881 	/* we have a persistent connection; try to accept another request. */
   1882 	if (evhttp_associate_new_request_with_connection(evcon) == -1)
   1883 		evhttp_connection_free(evcon);
   1884 }
   1885 
   1886 /*
   1887  * Returns an error page.
   1888  */
   1889 
   1890 void
   1891 evhttp_send_error(struct evhttp_request *req, int error, const char *reason)
   1892 {
   1893 #define ERR_FORMAT "<HTML><HEAD>\n" \
   1894 	    "<TITLE>%d %s</TITLE>\n" \
   1895 	    "</HEAD><BODY>\n" \
   1896 	    "<H1>Method Not Implemented</H1>\n" \
   1897 	    "Invalid method in request<P>\n" \
   1898 	    "</BODY></HTML>\n"
   1899 
   1900 	struct evbuffer *buf = evbuffer_new();
   1901 
   1902 	/* close the connection on error */
   1903 	evhttp_add_header(req->output_headers, "Connection", "close");
   1904 
   1905 	evhttp_response_code(req, error, reason);
   1906 
   1907 	evbuffer_add_printf(buf, ERR_FORMAT, error, reason);
   1908 
   1909 	evhttp_send_page(req, buf);
   1910 
   1911 	evbuffer_free(buf);
   1912 #undef ERR_FORMAT
   1913 }
   1914 
   1915 /* Requires that headers and response code are already set up */
   1916 
   1917 static inline void
   1918 evhttp_send(struct evhttp_request *req, struct evbuffer *databuf)
   1919 {
   1920 	struct evhttp_connection *evcon = req->evcon;
   1921 
   1922 	assert(TAILQ_FIRST(&evcon->requests) == req);
   1923 
   1924 	/* xxx: not sure if we really should expose the data buffer this way */
   1925 	if (databuf != NULL)
   1926 		evbuffer_add_buffer(req->output_buffer, databuf);
   1927 
   1928 	/* Adds headers to the response */
   1929 	evhttp_make_header(evcon, req);
   1930 
   1931 	evhttp_write_buffer(evcon, evhttp_send_done, NULL);
   1932 }
   1933 
   1934 void
   1935 evhttp_send_reply(struct evhttp_request *req, int code, const char *reason,
   1936     struct evbuffer *databuf)
   1937 {
   1938 	evhttp_response_code(req, code, reason);
   1939 
   1940 	evhttp_send(req, databuf);
   1941 }
   1942 
   1943 void
   1944 evhttp_send_reply_start(struct evhttp_request *req, int code,
   1945     const char *reason)
   1946 {
   1947 	evhttp_response_code(req, code, reason);
   1948 	if (req->major == 1 && req->minor == 1) {
   1949 		/* use chunked encoding for HTTP/1.1 */
   1950 		evhttp_add_header(req->output_headers, "Transfer-Encoding",
   1951 		    "chunked");
   1952 		req->chunked = 1;
   1953 	}
   1954 	evhttp_make_header(req->evcon, req);
   1955 	evhttp_write_buffer(req->evcon, NULL, NULL);
   1956 }
   1957 
   1958 void
   1959 evhttp_send_reply_chunk(struct evhttp_request *req, struct evbuffer *databuf)
   1960 {
   1961 	if (req->chunked) {
   1962 		evbuffer_add_printf(req->evcon->output_buffer, "%x\r\n",
   1963 				    (unsigned)EVBUFFER_LENGTH(databuf));
   1964 	}
   1965 	evbuffer_add_buffer(req->evcon->output_buffer, databuf);
   1966 	if (req->chunked) {
   1967 		evbuffer_add(req->evcon->output_buffer, "\r\n", 2);
   1968 	}
   1969 	evhttp_write_buffer(req->evcon, NULL, NULL);
   1970 }
   1971 
   1972 void
   1973 evhttp_send_reply_end(struct evhttp_request *req)
   1974 {
   1975 	struct evhttp_connection *evcon = req->evcon;
   1976 
   1977 	if (req->chunked) {
   1978 		evbuffer_add(req->evcon->output_buffer, "0\r\n\r\n", 5);
   1979 		evhttp_write_buffer(req->evcon, evhttp_send_done, NULL);
   1980 		req->chunked = 0;
   1981 	} else if (!event_pending(&evcon->ev, EV_WRITE|EV_TIMEOUT, NULL)) {
   1982 		/* let the connection know that we are done with the request */
   1983 		evhttp_send_done(evcon, NULL);
   1984 	} else {
   1985 		/* make the callback execute after all data has been written */
   1986 		evcon->cb = evhttp_send_done;
   1987 		evcon->cb_arg = NULL;
   1988 	}
   1989 }
   1990 
   1991 void
   1992 evhttp_response_code(struct evhttp_request *req, int code, const char *reason)
   1993 {
   1994 	req->kind = EVHTTP_RESPONSE;
   1995 	req->response_code = code;
   1996 	if (req->response_code_line != NULL)
   1997 		free(req->response_code_line);
   1998 	req->response_code_line = strdup(reason);
   1999 }
   2000 
   2001 void
   2002 evhttp_send_page(struct evhttp_request *req, struct evbuffer *databuf)
   2003 {
   2004 	if (!req->major || !req->minor) {
   2005 		req->major = 1;
   2006 		req->minor = 1;
   2007 	}
   2008 
   2009 	if (req->kind != EVHTTP_RESPONSE)
   2010 		evhttp_response_code(req, 200, "OK");
   2011 
   2012 	evhttp_clear_headers(req->output_headers);
   2013 	evhttp_add_header(req->output_headers, "Content-Type", "text/html");
   2014 	evhttp_add_header(req->output_headers, "Connection", "close");
   2015 
   2016 	evhttp_send(req, databuf);
   2017 }
   2018 
   2019 static const char uri_chars[256] = {
   2020 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2021 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2022 	0, 1, 0, 0, 1, 0, 0, 1,   1, 1, 1, 1, 1, 1, 1, 1,
   2023 	1, 1, 1, 1, 1, 1, 1, 1,   1, 1, 1, 0, 0, 1, 0, 0,
   2024 	/* 64 */
   2025 	1, 1, 1, 1, 1, 1, 1, 1,   1, 1, 1, 1, 1, 1, 1, 1,
   2026 	1, 1, 1, 1, 1, 1, 1, 1,   1, 1, 1, 0, 0, 0, 0, 1,
   2027 	0, 1, 1, 1, 1, 1, 1, 1,   1, 1, 1, 1, 1, 1, 1, 1,
   2028 	1, 1, 1, 1, 1, 1, 1, 1,   1, 1, 1, 0, 0, 0, 1, 0,
   2029 	/* 128 */
   2030 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2031 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2032 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2033 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2034 	/* 192 */
   2035 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2036 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2037 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2038 	0, 0, 0, 0, 0, 0, 0, 0,   0, 0, 0, 0, 0, 0, 0, 0,
   2039 };
   2040 
   2041 /*
   2042  * Helper functions to encode/decode a URI.
   2043  * The returned string must be freed by the caller.
   2044  */
   2045 char *
   2046 evhttp_encode_uri(const char *uri)
   2047 {
   2048 	struct evbuffer *buf = evbuffer_new();
   2049 	char *p;
   2050 
   2051 	for (p = (char *)uri; *p != '\0'; p++) {
   2052 		if (uri_chars[(u_char)(*p)]) {
   2053 			evbuffer_add(buf, p, 1);
   2054 		} else {
   2055 			evbuffer_add_printf(buf, "%%%02X", (u_char)(*p));
   2056 		}
   2057 	}
   2058 	evbuffer_add(buf, "", 1);
   2059 	p = strdup((char *)EVBUFFER_DATA(buf));
   2060 	evbuffer_free(buf);
   2061 
   2062 	return (p);
   2063 }
   2064 
   2065 /*
   2066  * @param always_decode_plus: when true we transform plus to space even
   2067  *     if we have not seen a ?.
   2068  */
   2069 static int
   2070 evhttp_decode_uri_internal(
   2071 	const char *uri, size_t length, char *ret, int always_decode_plus)
   2072 {
   2073 	char c;
   2074 	int i, j, in_query = always_decode_plus;
   2075 
   2076 	for (i = j = 0; uri[i] != '\0'; i++) {
   2077 		c = uri[i];
   2078 		if (c == '?') {
   2079 			in_query = 1;
   2080 		} else if (c == '+' && in_query) {
   2081 			c = ' ';
   2082 		} else if (c == '%' && isxdigit((unsigned char)uri[i+1]) &&
   2083 		    isxdigit((unsigned char)uri[i+2])) {
   2084 			char tmp[] = { uri[i+1], uri[i+2], '\0' };
   2085 			c = (char)strtol(tmp, NULL, 16);
   2086 			i += 2;
   2087 		}
   2088 		ret[j++] = c;
   2089 	}
   2090 	ret[j] = '\0';
   2091 
   2092 	return (j);
   2093 }
   2094 
   2095 char *
   2096 evhttp_decode_uri(const char *uri)
   2097 {
   2098 	char *ret;
   2099 
   2100 	if ((ret = malloc(strlen(uri) + 1)) == NULL)
   2101 		event_err(1, "%s: malloc(%lu)", __func__,
   2102 			  (unsigned long)(strlen(uri) + 1));
   2103 
   2104 	evhttp_decode_uri_internal(uri, strlen(uri),
   2105 	    ret, 0 /*always_decode_plus*/);
   2106 
   2107 	return (ret);
   2108 }
   2109 
   2110 /*
   2111  * Helper function to parse out arguments in a query.
   2112  * The arguments are separated by key and value.
   2113  */
   2114 
   2115 void
   2116 evhttp_parse_query(const char *uri, struct evkeyvalq *headers)
   2117 {
   2118 	char *line;
   2119 	char *argument;
   2120 	char *p;
   2121 
   2122 	TAILQ_INIT(headers);
   2123 
   2124 	/* No arguments - we are done */
   2125 	if (strchr(uri, '?') == NULL)
   2126 		return;
   2127 
   2128 	if ((line = strdup(uri)) == NULL)
   2129 		event_err(1, "%s: strdup", __func__);
   2130 
   2131 
   2132 	argument = line;
   2133 
   2134 	/* We already know that there has to be a ? */
   2135 	strsep(&argument, "?");
   2136 
   2137 	p = argument;
   2138 	while (p != NULL && *p != '\0') {
   2139 		char *key, *value, *decoded_value;
   2140 		argument = strsep(&p, "&");
   2141 
   2142 		value = argument;
   2143 		key = strsep(&value, "=");
   2144 		if (value == NULL)
   2145 			goto error;
   2146 
   2147 		if ((decoded_value = malloc(strlen(value) + 1)) == NULL)
   2148 			event_err(1, "%s: malloc", __func__);
   2149 
   2150 		evhttp_decode_uri_internal(value, strlen(value),
   2151 		    decoded_value, 1 /*always_decode_plus*/);
   2152 		event_debug(("Query Param: %s -> %s\n", key, decoded_value));
   2153 		evhttp_add_header_internal(headers, key, decoded_value);
   2154 		free(decoded_value);
   2155 	}
   2156 
   2157  error:
   2158 	free(line);
   2159 }
   2160 
   2161 static struct evhttp_cb *
   2162 evhttp_dispatch_callback(struct httpcbq *callbacks, struct evhttp_request *req)
   2163 {
   2164 	struct evhttp_cb *cb;
   2165 	size_t offset = 0;
   2166 
   2167 	/* Test for different URLs */
   2168 	char *p = strchr(req->uri, '?');
   2169 	if (p != NULL)
   2170 		offset = (size_t)(p - req->uri);
   2171 
   2172 	TAILQ_FOREACH(cb, callbacks, next) {
   2173 		int res = 0;
   2174 		if (p == NULL) {
   2175 			res = strcmp(cb->what, req->uri) == 0;
   2176 		} else {
   2177 			res = ((strncmp(cb->what, req->uri, offset) == 0) &&
   2178 					(cb->what[offset] == '\0'));
   2179 		}
   2180 
   2181 		if (res)
   2182 			return (cb);
   2183 	}
   2184 
   2185 	return (NULL);
   2186 }
   2187 
   2188 static void
   2189 evhttp_handle_request(struct evhttp_request *req, void *arg)
   2190 {
   2191 	struct evhttp *http = arg;
   2192 	struct evhttp_cb *cb = NULL;
   2193 
   2194 	if (req->uri == NULL) {
   2195 		evhttp_send_error(req, HTTP_BADREQUEST, "Bad Request");
   2196 		return;
   2197 	}
   2198 
   2199 	if ((cb = evhttp_dispatch_callback(&http->callbacks, req)) != NULL) {
   2200 		(*cb->cb)(req, cb->cbarg);
   2201 		return;
   2202 	}
   2203 
   2204 	/* Generic call back */
   2205 	if (http->gencb) {
   2206 		(*http->gencb)(req, http->gencbarg);
   2207 		return;
   2208 	} else {
   2209 		/* We need to send a 404 here */
   2210 #define ERR_FORMAT "<html><head>" \
   2211 		    "<title>404 Not Found</title>" \
   2212 		    "</head><body>" \
   2213 		    "<h1>Not Found</h1>" \
   2214 		    "<p>The requested URL %s was not found on this server.</p>"\
   2215 		    "</body></html>\n"
   2216 
   2217 		char *escaped_html = evhttp_htmlescape(req->uri);
   2218 		struct evbuffer *buf = evbuffer_new();
   2219 
   2220 		evhttp_response_code(req, HTTP_NOTFOUND, "Not Found");
   2221 
   2222 		evbuffer_add_printf(buf, ERR_FORMAT, escaped_html);
   2223 
   2224 		free(escaped_html);
   2225 
   2226 		evhttp_send_page(req, buf);
   2227 
   2228 		evbuffer_free(buf);
   2229 #undef ERR_FORMAT
   2230 	}
   2231 }
   2232 
   2233 static void
   2234 accept_socket(int fd, short what, void *arg)
   2235 {
   2236 	struct evhttp *http = arg;
   2237 	struct sockaddr_storage ss;
   2238 	socklen_t addrlen = sizeof(ss);
   2239 	int nfd;
   2240 
   2241 	if ((nfd = accept(fd, (struct sockaddr *)&ss, &addrlen)) == -1) {
   2242 		if (errno != EAGAIN && errno != EINTR)
   2243 			event_warn("%s: bad accept", __func__);
   2244 		return;
   2245 	}
   2246 	if (evutil_make_socket_nonblocking(nfd) < 0)
   2247 		return;
   2248 
   2249 	evhttp_get_request(http, nfd, (struct sockaddr *)&ss, addrlen);
   2250 }
   2251 
   2252 int
   2253 evhttp_bind_socket(struct evhttp *http, const char *address, u_short port)
   2254 {
   2255 	int fd;
   2256 	int res;
   2257 
   2258 	if ((fd = bind_socket(address, port, 1 /*reuse*/)) == -1)
   2259 		return (-1);
   2260 
   2261 	if (listen(fd, 128) == -1) {
   2262 		event_warn("%s: listen", __func__);
   2263 		EVUTIL_CLOSESOCKET(fd);
   2264 		return (-1);
   2265 	}
   2266 
   2267 	res = evhttp_accept_socket(http, fd);
   2268 
   2269 	if (res != -1)
   2270 		event_debug(("Bound to port %d - Awaiting connections ... ",
   2271 			port));
   2272 
   2273 	return (res);
   2274 }
   2275 
   2276 int
   2277 evhttp_accept_socket(struct evhttp *http, int fd)
   2278 {
   2279 	struct evhttp_bound_socket *bound;
   2280 	struct event *ev;
   2281 	int res;
   2282 
   2283 	bound = malloc(sizeof(struct evhttp_bound_socket));
   2284 	if (bound == NULL)
   2285 		return (-1);
   2286 
   2287 	ev = &bound->bind_ev;
   2288 
   2289 	/* Schedule the socket for accepting */
   2290 	event_set(ev, fd, EV_READ | EV_PERSIST, accept_socket, http);
   2291 	EVHTTP_BASE_SET(http, ev);
   2292 
   2293 	res = event_add(ev, NULL);
   2294 
   2295 	if (res == -1) {
   2296 		free(bound);
   2297 		return (-1);
   2298 	}
   2299 
   2300 	TAILQ_INSERT_TAIL(&http->sockets, bound, next);
   2301 
   2302 	return (0);
   2303 }
   2304 
   2305 static struct evhttp*
   2306 evhttp_new_object(void)
   2307 {
   2308 	struct evhttp *http = NULL;
   2309 
   2310 	if ((http = calloc(1, sizeof(struct evhttp))) == NULL) {
   2311 		event_warn("%s: calloc", __func__);
   2312 		return (NULL);
   2313 	}
   2314 
   2315 	http->timeout = -1;
   2316 
   2317 	TAILQ_INIT(&http->sockets);
   2318 	TAILQ_INIT(&http->callbacks);
   2319 	TAILQ_INIT(&http->connections);
   2320 
   2321 	return (http);
   2322 }
   2323 
   2324 struct evhttp *
   2325 evhttp_new(struct event_base *base)
   2326 {
   2327 	struct evhttp *http = evhttp_new_object();
   2328 
   2329 	http->base = base;
   2330 
   2331 	return (http);
   2332 }
   2333 
   2334 /*
   2335  * Start a web server on the specified address and port.
   2336  */
   2337 
   2338 struct evhttp *
   2339 evhttp_start(const char *address, u_short port)
   2340 {
   2341 	struct evhttp *http = evhttp_new_object();
   2342 
   2343 	if (evhttp_bind_socket(http, address, port) == -1) {
   2344 		free(http);
   2345 		return (NULL);
   2346 	}
   2347 
   2348 	return (http);
   2349 }
   2350 
   2351 void
   2352 evhttp_free(struct evhttp* http)
   2353 {
   2354 	struct evhttp_cb *http_cb;
   2355 	struct evhttp_connection *evcon;
   2356 	struct evhttp_bound_socket *bound;
   2357 	int fd;
   2358 
   2359 	/* Remove the accepting part */
   2360 	while ((bound = TAILQ_FIRST(&http->sockets)) != NULL) {
   2361 		TAILQ_REMOVE(&http->sockets, bound, next);
   2362 
   2363 		fd = bound->bind_ev.ev_fd;
   2364 		event_del(&bound->bind_ev);
   2365 		EVUTIL_CLOSESOCKET(fd);
   2366 
   2367 		free(bound);
   2368 	}
   2369 
   2370 	while ((evcon = TAILQ_FIRST(&http->connections)) != NULL) {
   2371 		/* evhttp_connection_free removes the connection */
   2372 		evhttp_connection_free(evcon);
   2373 	}
   2374 
   2375 	while ((http_cb = TAILQ_FIRST(&http->callbacks)) != NULL) {
   2376 		TAILQ_REMOVE(&http->callbacks, http_cb, next);
   2377 		free(http_cb->what);
   2378 		free(http_cb);
   2379 	}
   2380 
   2381 	free(http);
   2382 }
   2383 
   2384 void
   2385 evhttp_set_timeout(struct evhttp* http, int timeout_in_secs)
   2386 {
   2387 	http->timeout = timeout_in_secs;
   2388 }
   2389 
   2390 void
   2391 evhttp_set_cb(struct evhttp *http, const char *uri,
   2392     void (*cb)(struct evhttp_request *, void *), void *cbarg)
   2393 {
   2394 	struct evhttp_cb *http_cb;
   2395 
   2396 	if ((http_cb = calloc(1, sizeof(struct evhttp_cb))) == NULL)
   2397 		event_err(1, "%s: calloc", __func__);
   2398 
   2399 	http_cb->what = strdup(uri);
   2400 	http_cb->cb = cb;
   2401 	http_cb->cbarg = cbarg;
   2402 
   2403 	TAILQ_INSERT_TAIL(&http->callbacks, http_cb, next);
   2404 }
   2405 
   2406 int
   2407 evhttp_del_cb(struct evhttp *http, const char *uri)
   2408 {
   2409 	struct evhttp_cb *http_cb;
   2410 
   2411 	TAILQ_FOREACH(http_cb, &http->callbacks, next) {
   2412 		if (strcmp(http_cb->what, uri) == 0)
   2413 			break;
   2414 	}
   2415 	if (http_cb == NULL)
   2416 		return (-1);
   2417 
   2418 	TAILQ_REMOVE(&http->callbacks, http_cb, next);
   2419 	free(http_cb->what);
   2420 	free(http_cb);
   2421 
   2422 	return (0);
   2423 }
   2424 
   2425 void
   2426 evhttp_set_gencb(struct evhttp *http,
   2427     void (*cb)(struct evhttp_request *, void *), void *cbarg)
   2428 {
   2429 	http->gencb = cb;
   2430 	http->gencbarg = cbarg;
   2431 }
   2432 
   2433 /*
   2434  * Request related functions
   2435  */
   2436 
   2437 struct evhttp_request *
   2438 evhttp_request_new(void (*cb)(struct evhttp_request *, void *), void *arg)
   2439 {
   2440 	struct evhttp_request *req = NULL;
   2441 
   2442 	/* Allocate request structure */
   2443 	if ((req = calloc(1, sizeof(struct evhttp_request))) == NULL) {
   2444 		event_warn("%s: calloc", __func__);
   2445 		goto error;
   2446 	}
   2447 
   2448 	req->kind = EVHTTP_RESPONSE;
   2449 	req->input_headers = calloc(1, sizeof(struct evkeyvalq));
   2450 	if (req->input_headers == NULL) {
   2451 		event_warn("%s: calloc", __func__);
   2452 		goto error;
   2453 	}
   2454 	TAILQ_INIT(req->input_headers);
   2455 
   2456 	req->output_headers = calloc(1, sizeof(struct evkeyvalq));
   2457 	if (req->output_headers == NULL) {
   2458 		event_warn("%s: calloc", __func__);
   2459 		goto error;
   2460 	}
   2461 	TAILQ_INIT(req->output_headers);
   2462 
   2463 	if ((req->input_buffer = evbuffer_new()) == NULL) {
   2464 		event_warn("%s: evbuffer_new", __func__);
   2465 		goto error;
   2466 	}
   2467 
   2468 	if ((req->output_buffer = evbuffer_new()) == NULL) {
   2469 		event_warn("%s: evbuffer_new", __func__);
   2470 		goto error;
   2471 	}
   2472 
   2473 	req->cb = cb;
   2474 	req->cb_arg = arg;
   2475 
   2476 	return (req);
   2477 
   2478  error:
   2479 	if (req != NULL)
   2480 		evhttp_request_free(req);
   2481 	return (NULL);
   2482 }
   2483 
   2484 void
   2485 evhttp_request_free(struct evhttp_request *req)
   2486 {
   2487 	if (req->remote_host != NULL)
   2488 		free(req->remote_host);
   2489 	if (req->uri != NULL)
   2490 		free(req->uri);
   2491 	if (req->response_code_line != NULL)
   2492 		free(req->response_code_line);
   2493 
   2494 	evhttp_clear_headers(req->input_headers);
   2495 	free(req->input_headers);
   2496 
   2497 	evhttp_clear_headers(req->output_headers);
   2498 	free(req->output_headers);
   2499 
   2500 	if (req->input_buffer != NULL)
   2501 		evbuffer_free(req->input_buffer);
   2502 
   2503 	if (req->output_buffer != NULL)
   2504 		evbuffer_free(req->output_buffer);
   2505 
   2506 	free(req);
   2507 }
   2508 
   2509 void
   2510 evhttp_request_set_chunked_cb(struct evhttp_request *req,
   2511     void (*cb)(struct evhttp_request *, void *))
   2512 {
   2513 	req->chunk_cb = cb;
   2514 }
   2515 
   2516 /*
   2517  * Allows for inspection of the request URI
   2518  */
   2519 
   2520 const char *
   2521 evhttp_request_uri(struct evhttp_request *req) {
   2522 	if (req->uri == NULL)
   2523 		event_debug(("%s: request %p has no uri\n", __func__, req));
   2524 	return (req->uri);
   2525 }
   2526 
   2527 /*
   2528  * Takes a file descriptor to read a request from.
   2529  * The callback is executed once the whole request has been read.
   2530  */
   2531 
   2532 static struct evhttp_connection*
   2533 evhttp_get_request_connection(
   2534 	struct evhttp* http,
   2535 	int fd, struct sockaddr *sa, socklen_t salen)
   2536 {
   2537 	struct evhttp_connection *evcon;
   2538 	char *hostname = NULL, *portname = NULL;
   2539 
   2540 	name_from_addr(sa, salen, &hostname, &portname);
   2541 	if (hostname == NULL || portname == NULL) {
   2542 		if (hostname) free(hostname);
   2543 		if (portname) free(portname);
   2544 		return (NULL);
   2545 	}
   2546 
   2547 	event_debug(("%s: new request from %s:%s on %d\n",
   2548 			__func__, hostname, portname, fd));
   2549 
   2550 	/* we need a connection object to put the http request on */
   2551 	evcon = evhttp_connection_new(hostname, atoi(portname));
   2552 	free(hostname);
   2553 	free(portname);
   2554 	if (evcon == NULL)
   2555 		return (NULL);
   2556 
   2557 	/* associate the base if we have one*/
   2558 	evhttp_connection_set_base(evcon, http->base);
   2559 
   2560 	evcon->flags |= EVHTTP_CON_INCOMING;
   2561 	evcon->state = EVCON_READING_FIRSTLINE;
   2562 
   2563 	evcon->fd = fd;
   2564 
   2565 	return (evcon);
   2566 }
   2567 
   2568 static int
   2569 evhttp_associate_new_request_with_connection(struct evhttp_connection *evcon)
   2570 {
   2571 	struct evhttp *http = evcon->http_server;
   2572 	struct evhttp_request *req;
   2573 	if ((req = evhttp_request_new(evhttp_handle_request, http)) == NULL)
   2574 		return (-1);
   2575 
   2576 	req->evcon = evcon;	/* the request ends up owning the connection */
   2577 	req->flags |= EVHTTP_REQ_OWN_CONNECTION;
   2578 
   2579 	TAILQ_INSERT_TAIL(&evcon->requests, req, next);
   2580 
   2581 	req->kind = EVHTTP_REQUEST;
   2582 
   2583 	if ((req->remote_host = strdup(evcon->address)) == NULL)
   2584 		event_err(1, "%s: strdup", __func__);
   2585 	req->remote_port = evcon->port;
   2586 
   2587 	evhttp_start_read(evcon);
   2588 
   2589 	return (0);
   2590 }
   2591 
   2592 void
   2593 evhttp_get_request(struct evhttp *http, int fd,
   2594     struct sockaddr *sa, socklen_t salen)
   2595 {
   2596 	struct evhttp_connection *evcon;
   2597 
   2598 	evcon = evhttp_get_request_connection(http, fd, sa, salen);
   2599 	if (evcon == NULL)
   2600 		return;
   2601 
   2602 	/* the timeout can be used by the server to close idle connections */
   2603 	if (http->timeout != -1)
   2604 		evhttp_connection_set_timeout(evcon, http->timeout);
   2605 
   2606 	/*
   2607 	 * if we want to accept more than one request on a connection,
   2608 	 * we need to know which http server it belongs to.
   2609 	 */
   2610 	evcon->http_server = http;
   2611 	TAILQ_INSERT_TAIL(&http->connections, evcon, next);
   2612 
   2613 	if (evhttp_associate_new_request_with_connection(evcon) == -1)
   2614 		evhttp_connection_free(evcon);
   2615 }
   2616 
   2617 
   2618 /*
   2619  * Network helper functions that we do not want to export to the rest of
   2620  * the world.
   2621  */
   2622 #if 0 /* Unused */
   2623 static struct addrinfo *
   2624 addr_from_name(char *address)
   2625 {
   2626 #ifdef HAVE_GETADDRINFO
   2627         struct addrinfo ai, *aitop;
   2628         int ai_result;
   2629 
   2630         memset(&ai, 0, sizeof(ai));
   2631         ai.ai_family = AF_INET;
   2632         ai.ai_socktype = SOCK_RAW;
   2633         ai.ai_flags = 0;
   2634         if ((ai_result = getaddrinfo(address, NULL, &ai, &aitop)) != 0) {
   2635                 if ( ai_result == EAI_SYSTEM )
   2636                         event_warn("getaddrinfo");
   2637                 else
   2638                         event_warnx("getaddrinfo: %s", gai_strerror(ai_result));
   2639         }
   2640 
   2641 	return (aitop);
   2642 #else
   2643 	assert(0);
   2644 	return NULL; /* XXXXX Use gethostbyname, if this function is ever used. */
   2645 #endif
   2646 }
   2647 #endif
   2648 
   2649 static void
   2650 name_from_addr(struct sockaddr *sa, socklen_t salen,
   2651     char **phost, char **pport)
   2652 {
   2653 	char ntop[NI_MAXHOST];
   2654 	char strport[NI_MAXSERV];
   2655 	int ni_result;
   2656 
   2657 #ifdef HAVE_GETNAMEINFO
   2658 	ni_result = getnameinfo(sa, salen,
   2659 		ntop, sizeof(ntop), strport, sizeof(strport),
   2660 		NI_NUMERICHOST|NI_NUMERICSERV);
   2661 
   2662 	if (ni_result != 0) {
   2663 		if (ni_result == EAI_SYSTEM)
   2664 			event_err(1, "getnameinfo failed");
   2665 		else
   2666 			event_errx(1, "getnameinfo failed: %s", gai_strerror(ni_result));
   2667 		return;
   2668 	}
   2669 #else
   2670 	ni_result = fake_getnameinfo(sa, salen,
   2671 		ntop, sizeof(ntop), strport, sizeof(strport),
   2672 		NI_NUMERICHOST|NI_NUMERICSERV);
   2673 	if (ni_result != 0)
   2674 			return;
   2675 #endif
   2676 	*phost = strdup(ntop);
   2677 	*pport = strdup(strport);
   2678 }
   2679 
   2680 /* Create a non-blocking socket and bind it */
   2681 /* todo: rename this function */
   2682 static int
   2683 bind_socket_ai(struct addrinfo *ai, int reuse)
   2684 {
   2685         int fd, on = 1, r;
   2686 	int serrno;
   2687 
   2688         /* Create listen socket */
   2689         fd = socket(AF_INET, SOCK_STREAM, 0);
   2690         if (fd == -1) {
   2691                 event_warn("socket");
   2692                 return (-1);
   2693         }
   2694 
   2695         if (evutil_make_socket_nonblocking(fd) < 0)
   2696                 goto out;
   2697 
   2698 #ifndef WIN32
   2699         if (fcntl(fd, F_SETFD, 1) == -1) {
   2700                 event_warn("fcntl(F_SETFD)");
   2701                 goto out;
   2702         }
   2703 #endif
   2704 
   2705         setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, (void *)&on, sizeof(on));
   2706 	if (reuse) {
   2707 		setsockopt(fd, SOL_SOCKET, SO_REUSEADDR,
   2708 		    (void *)&on, sizeof(on));
   2709 	}
   2710 
   2711 	if (ai != NULL) {
   2712 		r = bind(fd, ai->ai_addr, ai->ai_addrlen);
   2713 		if (r == -1)
   2714 			goto out;
   2715 	}
   2716 
   2717 	return (fd);
   2718 
   2719  out:
   2720 	serrno = EVUTIL_SOCKET_ERROR();
   2721 	EVUTIL_CLOSESOCKET(fd);
   2722 	EVUTIL_SET_SOCKET_ERROR(serrno);
   2723 	return (-1);
   2724 }
   2725 
   2726 static struct addrinfo *
   2727 make_addrinfo(const char *address, u_short port)
   2728 {
   2729         struct addrinfo *aitop = NULL;
   2730 
   2731 #ifdef HAVE_GETADDRINFO
   2732         struct addrinfo ai;
   2733         char strport[NI_MAXSERV];
   2734         int ai_result;
   2735 
   2736         memset(&ai, 0, sizeof(ai));
   2737         ai.ai_family = AF_INET;
   2738         ai.ai_socktype = SOCK_STREAM;
   2739         ai.ai_flags = AI_PASSIVE;  /* turn NULL host name into INADDR_ANY */
   2740         evutil_snprintf(strport, sizeof(strport), "%d", port);
   2741         if ((ai_result = getaddrinfo(address, strport, &ai, &aitop)) != 0) {
   2742                 if ( ai_result == EAI_SYSTEM )
   2743                         event_warn("getaddrinfo");
   2744                 else
   2745                         event_warnx("getaddrinfo: %s", gai_strerror(ai_result));
   2746 		return (NULL);
   2747         }
   2748 #else
   2749 	static int cur;
   2750 	static struct addrinfo ai[2]; /* We will be returning the address of some of this memory so it has to last even after this call. */
   2751 	if (++cur == 2) cur = 0;   /* allow calling this function twice */
   2752 
   2753 	if (fake_getaddrinfo(address, &ai[cur]) < 0) {
   2754 		event_warn("fake_getaddrinfo");
   2755 		return (NULL);
   2756 	}
   2757 	aitop = &ai[cur];
   2758 	((struct sockaddr_in *) aitop->ai_addr)->sin_port = htons(port);
   2759 #endif
   2760 
   2761 	return (aitop);
   2762 }
   2763 
   2764 static int
   2765 bind_socket(const char *address, u_short port, int reuse)
   2766 {
   2767 	int fd;
   2768 	struct addrinfo *aitop = NULL;
   2769 
   2770 	/* just create an unbound socket */
   2771 	if (address == NULL && port == 0)
   2772 		return bind_socket_ai(NULL, 0);
   2773 
   2774 	aitop = make_addrinfo(address, port);
   2775 
   2776 	if (aitop == NULL)
   2777 		return (-1);
   2778 
   2779 	fd = bind_socket_ai(aitop, reuse);
   2780 
   2781 #ifdef HAVE_GETADDRINFO
   2782 	freeaddrinfo(aitop);
   2783 #else
   2784 	fake_freeaddrinfo(aitop);
   2785 #endif
   2786 
   2787 	return (fd);
   2788 }
   2789 
   2790 static int
   2791 socket_connect(int fd, const char *address, unsigned short port)
   2792 {
   2793 	struct addrinfo *ai = make_addrinfo(address, port);
   2794 	int res = -1;
   2795 
   2796 	if (ai == NULL) {
   2797 		event_debug(("%s: make_addrinfo: \"%s:%d\"",
   2798 			__func__, address, port));
   2799 		return (-1);
   2800 	}
   2801 
   2802 	if (connect(fd, ai->ai_addr, ai->ai_addrlen) == -1) {
   2803 #ifdef WIN32
   2804 		int tmp_error = WSAGetLastError();
   2805 		if (tmp_error != WSAEWOULDBLOCK && tmp_error != WSAEINVAL &&
   2806 		    tmp_error != WSAEINPROGRESS) {
   2807 			goto out;
   2808 		}
   2809 #else
   2810 		if (errno != EINPROGRESS) {
   2811 			goto out;
   2812 		}
   2813 #endif
   2814 	}
   2815 
   2816 	/* everything is fine */
   2817 	res = 0;
   2818 
   2819 out:
   2820 #ifdef HAVE_GETADDRINFO
   2821 	freeaddrinfo(ai);
   2822 #else
   2823 	fake_freeaddrinfo(ai);
   2824 #endif
   2825 
   2826 	return (res);
   2827 }
   2828