Esempio n. 1
0
void *CHttpServer::http_start_server(void *arg)
{
	CHttpServer *pthis = (CHttpServer *)arg;
	struct evhttp *httpd = NULL;
    	
	event_init();
	httpd = evhttp_start(pthis->m_http_addr, pthis->m_http_port);
	if (NULL == httpd) {
           printf("http server unable to listen on %s:%d\n\n", pthis->m_http_addr, pthis->m_http_port);
	   return NULL; 
    }
    evhttp_set_timeout(httpd, pthis->m_timeout);       
    evhttp_set_gencb(httpd, http_handle_postdata, arg);

#ifdef DEBUG
	printf("http_server start:%s:%d timeout:%u\n", 
			pthis->m_http_addr, 
			pthis->m_http_port, 
			pthis->m_timeout);
#else
	logrun("http_server start:%s:%d timeout:%u", 
			pthis->m_http_addr, 
			pthis->m_http_port, 
			pthis->m_timeout);
#endif
	event_dispatch();
	evhttp_free(httpd);
	
	return NULL;
}
Esempio n. 2
0
int
main(int argc, char **argv)
{
  // initialize libraries
  struct evhttp *httpd;

  if (sigignore(SIGPIPE) == -1) {
    perror("failed to ignore SIGPIPE; sigaction");
    exit(EXIT_FAILURE);
  }

  host = argv[2];
  port = atoi(argv[3]);
  event_init();
  httpd = evhttp_start("0.0.0.0", atoi(argv[1]));
  if (httpd == NULL) {
    perror("evhttpd failed!");
    exit(1);
  }

  /* Set a callback for all other requests. */
  evhttp_set_gencb(httpd, proxycb, NULL);

  event_dispatch();
  /* Not reached in this code as it is now. */
  evhttp_free(httpd);

  return EXIT_SUCCESS;
}
Esempio n. 3
0
TEvhttpServer::TEvhttpServer(boost::shared_ptr<TAsyncBufferProcessor> processor, int port)
  : processor_(processor), eb_(NULL), eh_(NULL) {
  // Create event_base and evhttp.
  eb_ = event_base_new();
  if (eb_ == NULL) {
    throw TException("event_base_new failed");
  }
  eh_ = evhttp_new(eb_);
  if (eh_ == NULL) {
    event_base_free(eb_);
    throw TException("evhttp_new failed");
  }

  // Bind to port.
  int ret = evhttp_bind_socket(eh_, NULL, port);
  if (ret < 0) {
    evhttp_free(eh_);
    event_base_free(eb_);
    throw TException("evhttp_bind_socket failed");
  }

  // Register a handler.  If you use the other constructor,
  // you will want to do this yourself.
  // Don't forget to unregister before destorying this TEvhttpServer.
  evhttp_set_cb(eh_, "/", request, (void*)this);
}
Esempio n. 4
0
int upnpc_finalize(upnpc_t * p)
{
	if(!p) return UPNPC_ERR_INVALID_ARGS;
	p->discover_device_index = 0;
	if(p->ssdp_socket >= 0) {
		close(p->ssdp_socket);
		p->ssdp_socket = -1;
	}
	if(p->ev_ssdp_recv) {
		event_free(p->ev_ssdp_recv);
		p->ev_ssdp_recv = NULL;
	}
	if(p->ev_ssdp_writable) {
		event_free(p->ev_ssdp_writable);
		p->ev_ssdp_writable = NULL;
	}
	while(p->devices != NULL) {
		upnpc_device_t * d = p->devices;
		upnpc_device_finalize(d);
		p->devices = d->next;
		free(d);
	}
	free(p->local_address);
	p->local_address = NULL;
#ifdef ENABLE_UPNP_EVENTS
	if(p->http_server) {
		evhttp_free(p->http_server);
		p->http_server = NULL;
	}
#endif /* ENABLE_UPNP_EVENTS */
	return UPNPC_OK;
}
Esempio n. 5
0
void StopHTTPServer()
{
    LogPrint(BCLog::HTTP, "Stopping HTTP server\n");
    if (workQueue) {
        LogPrint(BCLog::HTTP, "Waiting for HTTP worker threads to exit\n");
        workQueue->WaitExit();
        delete workQueue;
        workQueue = nullptr;
    }
    if (eventBase) {
        LogPrint(BCLog::HTTP, "Waiting for HTTP event thread to exit\n");
        // Give event loop a few seconds to exit (to send back last RPC responses), then break it
        // Before this was solved with event_base_loopexit, but that didn't work as expected in
        // at least libevent 2.0.21 and always introduced a delay. In libevent
        // master that appears to be solved, so in the future that solution
        // could be used again (if desirable).
        // (see discussion in https://github.com/bitcoin/bitcoin/pull/6990)
        if (threadResult.valid() && threadResult.wait_for(std::chrono::milliseconds(2000)) == std::future_status::timeout) {
            LogPrintf("HTTP event loop did not exit within allotted time, sending loopbreak\n");
            event_base_loopbreak(eventBase);
        }
        threadHTTP.join();
    }
    if (eventHTTP) {
        evhttp_free(eventHTTP);
        eventHTTP = 0;
    }
    if (eventBase) {
        event_base_free(eventBase);
        eventBase = 0;
    }
    LogPrint(BCLog::HTTP, "Stopped HTTP server\n");
}
Esempio n. 6
0
void clean_up(int sign_no)
{
    redis_free();
    evhttp_free(g_httpd);
    ini_free(setting->ini);
    exit(0);
}
Esempio n. 7
0
void av_fini( void )
{
	if( _av.eh ) evhttp_free(_av.eh);
	if( _av.hostportname ) free(_av.hostportname);
	if( _av.hostname ) free(_av.hostname);
	if( _av.rootdir) free(_av.rootdir);
}
int main (void) {
	struct event_base *ebase;
	struct evhttp *server;

	// Create a new event handler
	ebase = event_base_new ();;

	// Create a http server using that handler
	server = evhttp_new (ebase);

	// Limit serving GET requests
	evhttp_set_allowed_methods (server, EVHTTP_REQ_GET);

	// Set a test callback, /testing
	evhttp_set_cb (server, "/testing", testing, 0);

	// Set the callback for anything not recognized
	evhttp_set_gencb (server, notfound, 0);

	// Listen locally on port 32001
	if (evhttp_bind_socket (server, "127.0.0.1", 32001) != 0)
		errx (1, "Could not bind to 127.0.0.1:32001");

	// Start processing queries
	event_base_dispatch(ebase);

	// Free up stuff
	evhttp_free (server);

	event_base_free (ebase);
}
Esempio n. 9
0
static void
http_close_detection(int with_delay)
{
	short port = -1;
	struct evhttp_connection *evcon = NULL;
	struct evhttp_request *req = NULL;
	
	test_ok = 0;
	fprintf(stdout, "Testing Connection Close Detection%s: ",
		with_delay ? " (with delay)" : "");

	http = http_setup(&port, NULL);

	/* 2 second timeout */
	evhttp_set_timeout(http, 2);

	evcon = evhttp_connection_new("127.0.0.1", port);
	if (evcon == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	delayed_client = evcon;

	/*
	 * At this point, we want to schedule a request to the HTTP
	 * server using our make request method.
	 */

	req = evhttp_request_new(close_detect_cb, evcon);

	/* Add the information that we care about */
	evhttp_add_header(req->output_headers, "Host", "somehost");

	/* We give ownership of the request to the connection */
	if (evhttp_make_request(evcon,
	    req, EVHTTP_REQ_GET, with_delay ? "/largedelay" : "/test") == -1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	event_dispatch();

	if (test_ok != 1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/* at this point, the http server should have no connection */
	if (TAILQ_FIRST(&http->connections) != NULL) {
		fprintf(stdout, "FAILED (left connections)\n");
		exit(1);
	}

	evhttp_connection_free(evcon);
	evhttp_free(http);
	
	fprintf(stdout, "OK\n");
}
Esempio n. 10
0
GithubWebhooks::~GithubWebhooks()
{
	if (_breakLoop)
		event_active(_breakLoop, EV_READ, 0);
	_httpServer.join();
	if (_evhttp)
		evhttp_free(_evhttp);
}
Esempio n. 11
0
void ex_program(int sig) 
{
  fprintf(stderr, "[INFO]\tCaught signal: %d. Exiting program...\n",sig);
  /* Fang exit signal her og luk rigtigt ned */
  evhttp_free(server);
  fprintf(stderr,"[INFO]\tDone. Server is closed. Now go outside and play!!\n");
  exit(0);
}
Esempio n. 12
0
TEvhttpServer::~TEvhttpServer() {
  if (eh_ != NULL) {
    evhttp_free(eh_);
  }
  if (eb_ != NULL) {
    event_base_free(eb_);
  }
}
Esempio n. 13
0
void stat_srv_destroy (StatSrv *stat_srv)
{
    _queue_free_full (stat_srv->q_op_history, g_free);

    if (stat_srv->http)
        evhttp_free (stat_srv->http);

    g_free (stat_srv);
}
Esempio n. 14
0
void LibEventServer::stop() {
  Lock lock(m_mutex);
  if (getStatus() != RunStatus::RUNNING || m_server == nullptr) return;

#define SHUT_FBLISTEN 3
  /*
   * Modifications to the Linux kernel to support shutting down a listen
   * socket for new connections only, but anything which has completed
   * the TCP handshake will still be accepted.  This allows for un-accepted
   * connections to be queued and then wait until all queued requests are
   * actively being processed.
   */
  if (RuntimeOption::ServerShutdownListenWait > 0 &&
      m_accept_sock != -1 && shutdown(m_accept_sock, SHUT_FBLISTEN) == 0) {
    int noWorkCount = 0;
    for (int i = 0; i < RuntimeOption::ServerShutdownListenWait; i++) {
      // Give the acceptor thread time to clean out all requests
      Logger::Info(
          "LibEventServer stopping port %d: [%d/%d] a/q/e %d/%d/%d",
          m_port, i, RuntimeOption::ServerShutdownListenWait,
          getActiveWorker(), getQueuedJobs(), getLibEventConnectionCount());
      sleep(1);

      // If we're not doing anything, break out quickly
      noWorkCount += (getQueuedJobs() == 0 && getActiveWorker() == 0);
      if (RuntimeOption::ServerShutdownListenNoWork > 0 &&
          noWorkCount >= RuntimeOption::ServerShutdownListenNoWork)
        break;
      if (getLibEventConnectionCount() == 0 &&
          getQueuedJobs() == 0 && getActiveWorker() == 0)
        break;
    }
    Logger::Info("LibEventServer stopped port %d: a/q/e %d/%d/%d",
        m_port, getActiveWorker(), getQueuedJobs(),
        getLibEventConnectionCount());
  }

  // inform LibEventServer::onRequest() to stop queuing
  setStatus(RunStatus::STOPPING);

  // stop JobQueue processing
  m_dispatcher.stop();

  // stop event loop
  setStatus(RunStatus::STOPPED);
  if (write(m_pipeStop.getIn(), "", 1) < 0) {
    // an error occured but we're in shutdown already, so ignore
  }
  m_dispatcherThread.waitForEnd();

  // wait for the timeout thread to stop
  m_timeoutThreadData.stop();
  m_timeoutThread.waitForEnd();

  evhttp_free(m_server);
  m_server = nullptr;
}
Esempio n. 15
0
static void
http_base_test(void)
{
	struct bufferevent *bev;
	int fd;
	const char *http_request;
	short port = -1;

	test_ok = 0;
	fprintf(stdout, "Testing HTTP Server Event Base: ");

	base = event_init();

	/* 
	 * create another bogus base - which is being used by all subsequen
	 * tests - yuck!
	 */
	event_init();

	http = http_setup(&port, base);
	
	fd = http_connect("127.0.0.1", port);

	/* Stupid thing to send a request */
	bev = bufferevent_new(fd, http_readcb, http_writecb,
	    http_errorcb, NULL);
	bufferevent_base_set(base, bev);

	http_request =
	    "GET /test HTTP/1.1\r\n"
	    "Host: somehost\r\n"
	    "Connection: close\r\n"
	    "\r\n";

	bufferevent_write(bev, http_request, strlen(http_request));
	
	event_base_dispatch(base);

	bufferevent_free(bev);
	EVUTIL_CLOSESOCKET(fd);

	evhttp_free(http);

	event_base_free(base);
	base = NULL;
	
	if (test_ok != 2) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}
	
	fprintf(stdout, "OK\n");
}
Esempio n. 16
0
static void
http_dispatcher_test(void)
{
	short port = -1;
	struct evhttp_connection *evcon = NULL;
	struct evhttp_request *req = NULL;

	test_ok = 0;
	fprintf(stdout, "Testing HTTP Dispatcher: ");

	http = http_setup(&port, NULL);

	evcon = evhttp_connection_new("127.0.0.1", port);
	if (evcon == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/* also bind to local host */
	evhttp_connection_set_local_address(evcon, "127.0.0.1");

	/*
	 * At this point, we want to schedule an HTTP GET request
	 * server using our make request method.
	 */

	req = evhttp_request_new(http_dispatcher_test_done, NULL);
	if (req == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/* Add the information that we care about */
	evhttp_add_header(req->output_headers, "Host", "somehost");
	
	if (evhttp_make_request(evcon, req, EVHTTP_REQ_GET, "/?arg=val") == -1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	event_dispatch();

	evhttp_connection_free(evcon);
	evhttp_free(http);
	
	if (test_ok != 1) {
		fprintf(stdout, "FAILED: %d\n", test_ok);
		exit(1);
	}
	
	fprintf(stdout, "OK\n");
}
Esempio n. 17
0
void jw_httpsrv_destroy(jw_httpsrv httpsrv)
{
    assert(httpsrv);
    if (httpsrv->http)
    {
        evhttp_free(httpsrv->http);
    }
    if (httpsrv->next_body)
    {
        evbuffer_free(httpsrv->next_body);
    }
    jw_data_free(httpsrv);
}
Esempio n. 18
0
int main(int argc, char **argv)
{
	struct evhttp *httpd;

	event_init();
	httpd = evhttp_start(argv[argc-2], atoi(argv[argc-1]));
	evhttp_set_cb(httpd, "/request_sys/", sys_handler, NULL); 
/* Set a callback for all other requests. */
	evhttp_set_gencb(httpd, notfound_hander, NULL);
event_dispatch();    /* Not reached in this code as it is now. */
	evhttp_free(httpd);    
	return 0;
}
Esempio n. 19
0
int http_cleanup(struct http* http)
{
    if (!http)
        return ERROR_INVALID_PARAMETERS;

    if (http->docroot)
        free(http->docroot);

    if (http->http)
        evhttp_free(http->http);

    return S_OK;
}
Esempio n. 20
0
File: http.c Progetto: snip/aprsc
static void http_server_free(void)
{
	if (ev_timer) {
		event_del(ev_timer);
		hfree(ev_timer);
		ev_timer = NULL;
	}
	
	if (srvr_status) {
		evhttp_free(srvr_status);
		srvr_status = NULL;
	}
	
	if (srvr_upload) {
		evhttp_free(srvr_upload);
		srvr_upload = NULL;
	}
	
	if (libbase) {
		event_base_free(libbase);
		libbase = NULL;
	}
}
Esempio n. 21
0
static void
http_post_test(void)
{
	short port = -1;
	struct evhttp_connection *evcon = NULL;
	struct evhttp_request *req = NULL;

	test_ok = 0;
	fprintf(stdout, "Testing HTTP POST Request: ");

	http = http_setup(&port, NULL);

	evcon = evhttp_connection_new("127.0.0.1", port);
	if (evcon == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/*
	 * At this point, we want to schedule an HTTP POST request
	 * server using our make request method.
	 */

	req = evhttp_request_new(http_postrequest_done, NULL);
	if (req == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/* Add the information that we care about */
	evhttp_add_header(req->output_headers, "Host", "somehost");
	evbuffer_add_printf(req->output_buffer, POST_DATA);
	
	if (evhttp_make_request(evcon, req, EVHTTP_REQ_POST, "/postit") == -1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	event_dispatch();

	evhttp_connection_free(evcon);
	evhttp_free(http);
	
	if (test_ok != 1) {
		fprintf(stdout, "FAILED: %d\n", test_ok);
		exit(1);
	}
	
	fprintf(stdout, "OK\n");
}
Esempio n. 22
0
static void StopEventHandler(KonohaContext *kctx, void *args)
{
	KonohaFactory *factory = (KonohaFactory *)kctx->platApi;
	struct EventContext *eventContext = factory->EventModule.eventContext;
	if(eventContext != NULL) {
		eventContext->isWaiting = false;
		pthread_cond_signal(&eventContext->cond);
		pthread_mutex_destroy(&eventContext->lock);
		pthread_cond_destroy(&eventContext->cond);
		LocalQueue_Free(kctx, eventContext->queue);
		evhttp_free(eventContext->httpd);
		event_base_free(eventContext->base);
		PLATAPI free_i(eventContext);
		factory->EventModule.eventContext = NULL;
	}
}
Esempio n. 23
0
/* Thread: main */
void
httpd_deinit(void)
{
  int ret;

#ifdef USE_EVENTFD
  ret = eventfd_write(exit_efd, 1);
  if (ret < 0)
    {
      DPRINTF(E_FATAL, L_HTTPD, "Could not send exit event: %s\n", strerror(errno));

      return;
    }
#else
  int dummy = 42;

  ret = write(exit_pipe[1], &dummy, sizeof(dummy));
  if (ret != sizeof(dummy))
    {
      DPRINTF(E_FATAL, L_HTTPD, "Could not write to exit fd: %s\n", strerror(errno));

      return;
    }
#endif

  ret = pthread_join(tid_httpd, NULL);
  if (ret != 0)
    {
      DPRINTF(E_FATAL, L_HTTPD, "Could not join HTTPd thread: %s\n", strerror(errno));

      return;
    }

  streaming_deinit();
  rsp_deinit();
  dacp_deinit();
  daap_deinit();

#ifdef USE_EVENTFD
  close(exit_efd);
#else
  close(exit_pipe[0]);
  close(exit_pipe[1]);
#endif
  evhttp_free(evhttpd);
  event_base_free(evbase_httpd);
}
Esempio n. 24
0
int main(int argc,char** argv){

	evbase = event_base_new(); 
	if(!evbase){ 
		fprintf(stderr, "create evbase error!\n");
		exit(0); 
	}

	// 创建http server实例
	ev_ssl = evhttp_new(evbase);
	if(!ev_ssl){ 
		exit(0); 
	}

	// openssl 初始化 
	SSL_library_init(); 
	ERR_load_crypto_strings(); 
	SSL_load_error_strings(); 
	OpenSSL_add_all_algorithms();

	if (SSLeay() != OPENSSL_VERSION_NUMBER){ 
	
	}

	ev_ssl->ctx = get_ssl_ctx(certfile_url.c_str(),keyfile_url.c_str()); 
	ev_ssl->ssl_cb = bufferevent_openssl_socket_new;

	std::string ev_ssl_ip="192.168.1.10"; int ev_ssl_port = 8080;

	// evhttp_bind_socket_with_handle这个函数在原基础上追加一个参数,标示http server知否支持ssl(0:不支持 1:支持) 
	struct evhttp_bound_socket *ssl_handle = evhttp_bind_socket_with_handle(ev_ssl, ev_ssl_ip.c_str(), ev_ssl_port,1); 
	if(!ssl_handle){ 
		exit(0); 
	}
	
	struct evconnlistener *ssl_listener = evhttp_bound_socket_get_listener(ssl_handle); 
	evconnlistener_set_error_cb(ssl_listener, ssl_accept_error_cb);

	evhttp_set_cb(ev_ssl, "/ping", ping_handler, NULL);

	event_base_dispatch(evbase);

	evhttp_free(ev_ssl); event_base_free(evbase);

	return 0; 
}
Esempio n. 25
0
File: rpc.c Progetto: dyustc/searaft
int init_rpc_server(struct rpc_context *rpc_context, const struct rpc_target *dest) {
    //should check dest->proto and do http handling only when proto=HTTP
    rpc_context->http = evhttp_new(rpc_context->base);
    if(!rpc_context->http) {
        return 1;
    }
    evhttp_set_cb(rpc_context->http, "/rpc", server_rpc_cb, rpc_context);

    rpc_context->handle = evhttp_bind_socket_with_handle(
        rpc_context->http, dest->host, dest->port);
    if(!rpc_context->handle) {
        evhttp_free(rpc_context->http);
        return 1;
    }

    return 0;
}
Esempio n. 26
0
static void
cleanup_httpd_thread(thd_data *thd) {
  if (thd->log_file) {
    fclose(thd->log_file);
  }
  if (thd->httpd) {
    evhttp_free(thd->httpd);
  }
  if (thd->zmq_sock) {
    zmq_close(thd->zmq_sock);
  }
  grn_obj_unlink(thd->ctx, &(thd->cmd_buf));
  if (thd->ctx) {
    grn_ctx_close(thd->ctx);
  }
  event_base_free(thd->base);
}
Esempio n. 27
0
int main (int argc, char **av)
{
	struct event_base *ev_base;
	struct evhttp *httpd;

	ev_base = event_base_new();
	httpd = evhttp_new(ev_base);
	if (evhttp_bind_socket(httpd, HTTPD_ADDR, HTTPD_PORT) < 0) {
		perror("evhttp_bind_socket");
		exit(EXIT_FAILURE);
	}
	evhttp_set_gencb(httpd, req_handler, NULL);
	event_base_dispatch(ev_base);
	evhttp_free(httpd);
	event_base_free(ev_base);
	return 0;
}
Esempio n. 28
0
void LibEventServer::stop() {
  Lock lock(m_mutex);
  if (getStatus() != RUNNING || m_server == NULL) return;

  // inform LibEventServer::onRequest() to stop queuing
  setStatus(STOPPING);

  // stop JobQueue processing
  m_dispatcher.stop();

  // stop event loop
  setStatus(STOPPED);
  write(m_pipeStop.getIn(), "", 1);
  m_dispatcherThread.waitForEnd();
  evhttp_free(m_server);
  m_server = NULL;
}
Esempio n. 29
0
static void
http_multi_line_header_test(void)
{
	struct bufferevent *bev;
	int fd;
	const char *http_start_request;
	short port = -1;
	
	test_ok = 0;
	fprintf(stdout, "Testing HTTP Server with multi line: ");

	http = http_setup(&port, NULL);
	
	fd = http_connect("127.0.0.1", port);

	/* Stupid thing to send a request */
	bev = bufferevent_new(fd, http_readcb, http_writecb,
	    http_errorcb, NULL);

	http_start_request =
	    "GET /test HTTP/1.1\r\n"
	    "Host: somehost\r\n"
	    "Connection: close\r\n"
	    "X-Multi:  aaaaaaaa\r\n"
	    " a\r\n"
	    "\tEND\r\n"
	    "X-Last: last\r\n"
	    "\r\n";
		
	bufferevent_write(bev, http_start_request, strlen(http_start_request));

	event_dispatch();
	
	bufferevent_free(bev);
	EVUTIL_CLOSESOCKET(fd);

	evhttp_free(http);

	if (test_ok != 4) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}
	
	fprintf(stdout, "OK\n");
}
Esempio n. 30
0
static void
http_negative_content_length_test(void)
{
	short port = -1;
	struct evhttp_connection *evcon = NULL;
	struct evhttp_request *req = NULL;
	
	test_ok = 0;
	fprintf(stdout, "Testing HTTP Negative Content Length: ");

	http = http_setup(&port, NULL);

	evcon = evhttp_connection_new("127.0.0.1", port);
	if (evcon == NULL) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	/*
	 * At this point, we want to schedule a request to the HTTP
	 * server using our make request method.
	 */

	req = evhttp_request_new(http_request_bad, NULL);

	/* Cause the response to have a negative content-length */
	evhttp_add_header(req->output_headers, "X-Negative", "makeitso");

	/* We give ownership of the request to the connection */
	if (evhttp_make_request(evcon, req, EVHTTP_REQ_GET, "/test") == -1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	event_dispatch();

	evhttp_free(http);

	if (test_ok != 1) {
		fprintf(stdout, "FAILED\n");
		exit(1);
	}

	fprintf(stdout, "OK\n");
}