more complete http body handling

This commit is contained in:
Nikos Mavrogiannopoulos
2013-02-23 09:59:02 +01:00
parent 82db04ad4d
commit d2df8a3e4f
3 changed files with 43 additions and 28 deletions
+6 -6
View File
@@ -344,7 +344,7 @@ struct cmd_auth_cookie_req_st areq;
int post_old_auth_handler(worker_st *ws)
{
int ret;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
const char* reason = "Authentication failed";
char str_cookie[2*COOKIE_SIZE+1];
char * username = NULL;
@@ -357,14 +357,14 @@ struct cmd_auth_req_st areq;
if (ws->config->auth_types & AUTH_TYPE_USERNAME_PASS) {
/* body should be "username=test&password=test" */
username = strstr(req->body, "username=");
username = memmem(req->body, req->body_length, "username=", sizeof("username=")-1);
if (username == NULL) {
reason = "No username";
goto auth_fail;
}
username += sizeof("username=")-1;
password = strstr(req->body, "password=");
password = memmem(req->body, req->body_length, "password=", sizeof("password=")-1);
if (password == NULL) {
reason = "No password";
goto auth_fail;
@@ -464,7 +464,7 @@ auth_fail:
int post_new_auth_handler(worker_st *ws)
{
int ret;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
const char* reason = "Authentication failed";
char str_cookie[2*COOKIE_SIZE+1];
char * username = NULL;
@@ -477,14 +477,14 @@ struct cmd_auth_req_st areq;
if (ws->config->auth_types & AUTH_TYPE_USERNAME_PASS) {
/* body should contain <username>test</username><password>test</password> */
username = strstr(req->body, XMLUSER);
username = memmem(req->body, req->body_length, XMLUSER, sizeof(XMLUSER)-1);
if (username == NULL) {
reason = "No username";
goto ask_auth;
}
username += sizeof(XMLUSER)-1;
password = strstr(req->body, XMLPASS);
password = memmem(req->body, req->body_length, XMLPASS, sizeof(XMLPASS)-1);
if (password == NULL) {
reason = "No password";
goto auth_fail;
+34 -20
View File
@@ -122,7 +122,7 @@ struct known_urls_st *p;
int url_cb(http_parser* parser, const char *at, size_t length)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
if (length >= sizeof(req->url)) {
req->url[0] = 0;
@@ -143,7 +143,7 @@ int url_cb(http_parser* parser, const char *at, size_t length)
int header_field_cb(http_parser* parser, const char *at, size_t length)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
if (length == sizeof(STR_HDR_COOKIE)-1 && strncmp(at, STR_HDR_COOKIE, length) == 0) {
req->next_header = HEADER_COOKIE;
@@ -173,7 +173,7 @@ int header_field_cb(http_parser* parser, const char *at, size_t length)
int header_value_cb(http_parser* parser, const char *at, size_t length)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
char *p;
size_t nlen;
@@ -242,7 +242,7 @@ int header_value_cb(http_parser* parser, const char *at, size_t length)
int header_complete_cb(http_parser* parser)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
req->headers_complete = 1;
return 0;
@@ -251,7 +251,7 @@ int header_complete_cb(http_parser* parser)
int message_complete_cb(http_parser* parser)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
req->message_complete = 1;
return 0;
@@ -260,16 +260,16 @@ int message_complete_cb(http_parser* parser)
int body_cb(http_parser* parser, const char *at, size_t length)
{
struct worker_st *ws = parser->data;
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
char* tmp;
tmp = realloc(req->body, length+1);
tmp = realloc(req->body, req->body_length+length+1);
if (tmp == NULL)
return 1;
memcpy(tmp, at, length);
tmp[length] = 0;
memcpy(&tmp[req->body_length], at, length);
req->body_length += length;
tmp[req->body_length] = 0;
req->body = tmp;
return 0;
@@ -330,6 +330,22 @@ fail:
return -1;
}
static void http_req_reset(worker_st * ws)
{
ws->req.headers_complete = 0;
ws->req.message_complete = 0;
ws->req.body_length = 0;
ws->req.url[0] = 0;
ws->req.dbg_txt[0] = 0;
}
static void http_req_deinit(worker_st * ws)
{
http_req_reset(ws);
free(ws->req.body);
ws->req.body = NULL;
}
static
void exit_worker(worker_st *ws)
{
@@ -412,10 +428,8 @@ restart:
http_parser_init(&parser, HTTP_REQUEST);
parser.data = ws;
ws->req.headers_complete = 0;
ws->req.message_complete = 0;
ws->req.url[0] = 0;
ws->req.dbg_txt[0] = 0;
http_req_reset(ws);
/* parse as we go */
do {
@@ -543,7 +557,7 @@ unsigned int c;
#define SEND_ERR(x) if (x<0) goto send_error
static int connect_handler(worker_st *ws)
{
struct req_data_st *req = &ws->req;
struct http_req_st *req = &ws->req;
fd_set rfds;
int l, e, max, ret;
struct vpn_st vinfo;
@@ -582,10 +596,6 @@ unsigned mtu_overhead, tls_mtu = 0;
}
}
/* turn of the alarm */
if (ws->config->auth_timeout)
alarm(0);
if (strcmp(req->url, "/CSCOSSLC/tunnel") != 0) {
oclog(ws, LOG_INFO, "bad connect request: '%s'\n", req->url);
tls_puts(ws->session, "HTTP/1.1 404 Nah, go away\r\n\r\n");
@@ -608,6 +618,11 @@ unsigned mtu_overhead, tls_mtu = 0;
return -1;
}
/* Connected. Turn of the alarm */
if (ws->config->auth_timeout)
alarm(0);
http_req_deinit(ws);
tls_cork(ws->session);
ret = tls_puts(ws->session, "HTTP/1.1 200 CONNECTED\r\n");
SEND_ERR(ret);
@@ -623,7 +638,6 @@ unsigned mtu_overhead, tls_mtu = 0;
memcpy(ws->master_secret, req->master_secret, TLS_MASTER_SIZE);
ws->udp_state = UP_WAIT_FD;
}
if (vinfo.ipv4) {
oclog(ws, LOG_DEBUG, "sending IPv4 %s", vinfo.ipv4);
+3 -2
View File
@@ -28,7 +28,7 @@ enum {
HEADER_DTLS_MTU,
};
struct req_data_st {
struct http_req_st {
char url[256];
char dbg_txt[256];
@@ -40,6 +40,7 @@ struct req_data_st {
unsigned int master_secret_set;
char *body;
unsigned int body_length;
unsigned int headers_complete;
unsigned int message_complete;
unsigned dtls_mtu;
@@ -88,7 +89,7 @@ typedef struct worker_st {
unsigned auth_ok;
int tun_fd;
struct req_data_st req;
struct http_req_st req;
} worker_st;
void vpn_server(struct worker_st* ws);