summaryrefslogtreecommitdiffstats
path: root/nanohttp/nanohttp-common.c
diff options
context:
space:
mode:
authorGravatar rans2004-08-26 17:07:47 +0000
committerGravatar rans2004-08-26 17:07:47 +0000
commit8fa610c18388161569d68034243af9c923dbbee9 (patch)
tree7a6734c77bed901fe21a0b1b4b5dc848a3b153af /nanohttp/nanohttp-common.c
parent3ad9ad0547145e25657660e3c1c92ffb6905d3dc (diff)
downloadcsoap-8fa610c18388161569d68034243af9c923dbbee9.tar.gz
csoap-8fa610c18388161569d68034243af9c923dbbee9.tar.bz2
http stuff
Diffstat (limited to 'nanohttp/nanohttp-common.c')
-rw-r--r--nanohttp/nanohttp-common.c1050
1 files changed, 535 insertions, 515 deletions
diff --git a/nanohttp/nanohttp-common.c b/nanohttp/nanohttp-common.c
index 1d00d42..6fac5ba 100644
--- a/nanohttp/nanohttp-common.c
+++ b/nanohttp/nanohttp-common.c
@@ -1,26 +1,26 @@
/******************************************************************
- * $Id: nanohttp-common.c,v 1.8 2004/02/03 08:59:23 snowdrop Exp $
- *
- * CSOAP Project: A http client/server library in C
- * Copyright (C) 2003 Ferhat Ayaz
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
- * Boston, MA 02111-1307, USA.
- *
- * Email: ayaz@jprogrammer.net
- ******************************************************************/
+* $Id: nanohttp-common.c,v 1.9 2004/08/26 17:07:47 rans Exp $
+*
+* CSOAP Project: A http client/server library in C
+* Copyright (C) 2003 Ferhat Ayaz
+*
+* This library is free software; you can redistribute it and/or
+* modify it under the terms of the GNU Library General Public
+* License as published by the Free Software Foundation; either
+* version 2 of the License, or (at your option) any later version.
+*
+* This library is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+* Library General Public License for more details.
+*
+* You should have received a copy of the GNU Library General Public
+* License along with this library; if not, write to the
+* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+* Boston, MA 02111-1307, USA.
+*
+* Email: ayaz@jprogrammer.net
+******************************************************************/
#include <nanohttp/nanohttp-common.h>
@@ -28,663 +28,683 @@
#include <stdlib.h>
#include <stdarg.h>
+#ifdef WIN32
+#include <string.h>
+static char *strtok_r (char *s, const char *delim, char **save_ptr)
+{
+ char *token;
+
+ if (s == NULL)
+ s = *save_ptr;
+
+ /* Scan leading delimiters. */
+ s += strspn (s, delim);
+ if (*s == '\0')
+ return NULL;
+
+ /* Find the end of the token. */
+ token = s;
+ s = strpbrk (token, delim);
+ if (s == NULL)
+ /* This token finishes the string. */
+ *save_ptr = strchr (token, '\0');
+ else
+ {
+ /* Terminate the token and make *SAVE_PTR point past it. */
+ *s = '\0';
+ *save_ptr = s + 1;
+ }
+ return token;
+}
+#endif
static log_level_t loglevel = HLOG_DEBUG;
log_level_t log_set_level(log_level_t level)
{
- log_level_t old = loglevel;
- loglevel = level;
- return old;
+ log_level_t old = loglevel;
+ loglevel = level;
+ return old;
}
log_level_t log_get_level()
{
- return loglevel;
+ return loglevel;
}
-
static
void log_write(log_level_t level, const char *prefix,
- const char* func, const char *format, va_list ap)
+ const char* func, const char *format, va_list ap)
{
- char buffer[1054];
- char buffer2[1054];
-
- if (level < loglevel) return;
-
- sprintf(buffer, "*%s*: [%s] %s\n", prefix, func, format);
- vsprintf(buffer2, buffer, ap);
- printf(buffer2);
- fflush(stdout);
+ char buffer[1054];
+ char buffer2[1054];
+
+ if (level < loglevel) return;
+
+ sprintf(buffer, "*%s*: [%s] %s\n", prefix, func, format);
+ vsprintf(buffer2, buffer, ap);
+ printf(buffer2);
+ fflush(stdout);
}
void log_verbose(const char* FUNC, const char *format, ...)
{
- va_list ap;
-
- va_start(ap, format);
- log_write(HLOG_VERBOSE, "VERBOSE", FUNC, format, ap);
- va_end(ap);
+ va_list ap;
+
+ va_start(ap, format);
+ log_write(HLOG_VERBOSE, "VERBOSE", FUNC, format, ap);
+ va_end(ap);
}
void log_debug(const char* FUNC, const char *format, ...)
{
- va_list ap;
-
- va_start(ap, format);
- log_write(HLOG_DEBUG, "DEBUG", FUNC, format, ap);
- va_end(ap);
+ va_list ap;
+
+ va_start(ap, format);
+ log_write(HLOG_DEBUG, "DEBUG", FUNC, format, ap);
+ va_end(ap);
}
void log_info(const char* FUNC, const char *format, ...)
{
- va_list ap;
-
- va_start(ap, format);
- log_write(HLOG_INFO, "INFO", FUNC, format, ap);
- va_end(ap);
+ va_list ap;
+
+ va_start(ap, format);
+ log_write(HLOG_INFO, "INFO", FUNC, format, ap);
+ va_end(ap);
}
void log_warn(const char* FUNC, const char *format, ...)
{
- va_list ap;
-
- va_start(ap, format);
- log_write(HLOG_WARN, "WARN", FUNC, format, ap);
- va_end(ap);
+ va_list ap;
+
+ va_start(ap, format);
+ log_write(HLOG_WARN, "WARN", FUNC, format, ap);
+ va_end(ap);
}
void log_error(const char* FUNC, const char *format, ...)
{
- va_list ap;
-
- va_start(ap, format);
- log_write(HLOG_ERROR, "ERROR", FUNC, format, ap);
- va_end(ap);
+ va_list ap;
+
+ va_start(ap, format);
+ log_write(HLOG_ERROR, "ERROR", FUNC, format, ap);
+ va_end(ap);
}
/* -----------------------------------------
- FUNCTION: strcmpigcase
- ------------------------------------------ */
+FUNCTION: strcmpigcase
+------------------------------------------ */
int strcmpigcase(const char *s1, const char *s2)
{
- int l1, l2, i;
+ int l1, l2, i;
+
+ if (s1 == NULL && s2 == NULL) return 1;
+ if (s1 == NULL || s2 == NULL) return 0;
- if (s1 == NULL && s2 == NULL) return 1;
- if (s1 == NULL || s2 == NULL) return 0;
+ l1 = strlen(s1);
+ l2 = strlen(s2);
- l1 = strlen(s1);
- l2 = strlen(s2);
+ if (l1 != l2) return 0;
- if (l1 != l2) return 0;
-
- for (i=0;i<l1;i++)
- if (toupper(s1[i]) != toupper(s2[i]))
- return 0;
+ for (i=0;i<l1;i++)
+ if (toupper(s1[i]) != toupper(s2[i]))
+ return 0;
- return 1;
+ return 1;
}
hpair_t *hpairnode_new(const char* key, const char* value, hpair_t *next)
{
- hpair_t *pair;
+ hpair_t *pair;
- log_verbose3("new pair ('%s','%s')", SAVE_STR(key), SAVE_STR(value));
- pair = (hpair_t*)malloc(sizeof(hpair_t));
+ log_verbose3("new pair ('%s','%s')", SAVE_STR(key), SAVE_STR(value));
+ pair = (hpair_t*)malloc(sizeof(hpair_t));
- if (key != NULL) {
- pair->key = (char*)malloc(strlen(key)+1);
- strcpy(pair->key, key);
- } else {
- pair->key = NULL;
- }
+ if (key != NULL) {
+ pair->key = (char*)malloc(strlen(key)+1);
+ strcpy(pair->key, key);
+ } else {
+ pair->key = NULL;
+ }
- if (value != NULL) {
- pair->value = (char*)malloc(strlen(value)+1);
- strcpy(pair->value, value);
- } else {
- pair->value = NULL;
- }
+ if (value != NULL) {
+ pair->value = (char*)malloc(strlen(value)+1);
+ strcpy(pair->value, value);
+ } else {
+ pair->value = NULL;
+ }
- pair->next = next;
+ pair->next = next;
- return pair;
+ return pair;
}
hpair_t *hpairnode_parse(const char *str, const char *delim, hpair_t *next)
{
- hpair_t *pair;
- char *key, *value;
- int c;
-
- pair = (hpair_t*)malloc(sizeof(hpair_t));
- pair->key = "";
- pair->value = "";
- pair->next = next;
-
- key = strtok_r(str, delim, &value);
-
- if (key != NULL) {
- pair->key = (char*)malloc(strlen(key)+1);
- strcpy(pair->key, key);
- }
-
- if (value != NULL) {
- for (c=0;value[c]==' ';c++); /* skip white space */
- pair->value = (char*)malloc(strlen(&value[c])+1);
- strcpy(pair->value, &value[c]);
- }
-
- return pair;
+ hpair_t *pair;
+ char *key, *value;
+ int c;
+
+ pair = (hpair_t*)malloc(sizeof(hpair_t));
+ pair->key = "";
+ pair->value = "";
+ pair->next = next;
+
+ key = strtok_r((char *)str, delim, &value);
+
+ if (key != NULL) {
+ pair->key = (char*)malloc(strlen(key)+1);
+ strcpy(pair->key, key);
+ }
+
+ if (value != NULL) {
+ for (c=0;value[c]==' ';c++); /* skip white space */
+ pair->value = (char*)malloc(strlen(&value[c])+1);
+ strcpy(pair->value, &value[c]);
+ }
+
+ return pair;
}
hpair_t* hpairnode_copy(const hpair_t *src)
{
- hpair_t *pair;
+ hpair_t *pair;
- if (src == NULL) return NULL;
+ if (src == NULL) return NULL;
- pair = hpairnode_new(src->key, src->value, NULL);
- return pair;
+ pair = hpairnode_new(src->key, src->value, NULL);
+ return pair;
}
hpair_t* hpairnode_copy_deep(const hpair_t *src)
{
- hpair_t *pair, *result, *next;
+ hpair_t *pair, *result, *next;
+
+ if (src == NULL) return NULL;
- if (src == NULL) return NULL;
+ result = hpairnode_copy(src);
- result = hpairnode_copy(src);
+ next = src->next;
+ pair = result;
- next = src->next;
- pair = result;
+ while (next != NULL) {
+ pair->next = hpairnode_copy(next);
+ pair = pair->next;
+ next = next->next;
+ }
- while (next != NULL) {
- pair->next = hpairnode_copy(next);
- pair = pair->next;
- next = next->next;
- }
-
- return result;
+ return result;
}
void hpairnode_dump(hpair_t *pair)
{
- if (pair == NULL) {
- log_verbose1("(NULL)[]");
- return;
- }
-
- log_verbose5("(%p)['%s','%s','%p']", pair,
- SAVE_STR(pair->key), SAVE_STR(pair->value),
- pair->next);
+ if (pair == NULL) {
+ log_verbose1("(NULL)[]");
+ return;
+ }
+
+ log_verbose5("(%p)['%s','%s','%p']", pair,
+ SAVE_STR(pair->key), SAVE_STR(pair->value),
+ pair->next);
}
void hpairnode_dump_deep(hpair_t *pair)
{
- hpair_t *p;
- p = pair;
+ hpair_t *p;
+ p = pair;
- log_verbose1("-- BEGIN dump hpairnode_t --");
+ log_verbose1("-- BEGIN dump hpairnode_t --");
- while (p != NULL) {
- hpairnode_dump(p);
- p = p->next;
- }
+ while (p != NULL) {
+ hpairnode_dump(p);
+ p = p->next;
+ }
- log_verbose1("-- END dump hpairnode_t --\n");
+ log_verbose1("-- END dump hpairnode_t --\n");
}
void hpairnode_free(hpair_t *pair)
{
- if (pair == NULL) return;
-
- free(pair->key);
- free(pair->value);
-
- free(pair);
+ if (pair == NULL) return;
+
+ free(pair->key);
+ free(pair->value);
+
+ free(pair);
}
void hpairnode_free_deep(hpair_t *pair)
{
- hpair_t *tmp;
+ hpair_t *tmp;
- while (pair != NULL) {
- tmp = pair->next;
- hpairnode_free(pair);
- pair=tmp;
- }
+ while (pair != NULL) {
+ tmp = pair->next;
+ hpairnode_free(pair);
+ pair=tmp;
+ }
}
char *hpairnode_get_ignore_case(hpair_t *pair, const char* key)
{
- if (key == NULL) {
- log_error1("key is NULL");
- return NULL;
- }
-
- while (pair != NULL) {
- if (pair->key != NULL) {
- if (strcmpigcase(pair->key, key)) {
- return pair->value;
- }
- }
- pair = pair->next;
- }
-
- return NULL;
+ if (key == NULL) {
+ log_error1("key is NULL");
+ return NULL;
+ }
+
+ while (pair != NULL) {
+ if (pair->key != NULL) {
+ if (strcmpigcase(pair->key, key)) {
+ return pair->value;
+ }
+ }
+ pair = pair->next;
+ }
+
+ return NULL;
}
char *hpairnode_get(hpair_t *pair, const char* key)
{
- if (key == NULL) {
- log_error1("key is NULL");
- return NULL;
- }
-
- while (pair != NULL) {
- if (pair->key != NULL) {
- if (!strcmp(pair->key, key)) {
- return pair->value;
- }
- }
- pair = pair->next;
- }
-
- return NULL;
+ if (key == NULL) {
+ log_error1("key is NULL");
+ return NULL;
+ }
+
+ while (pair != NULL) {
+ if (pair->key != NULL) {
+ if (!strcmp(pair->key, key)) {
+ return pair->value;
+ }
+ }
+ pair = pair->next;
+ }
+
+ return NULL;
}
static
void hurl_dump(const hurl_t *url)
{
- if (url == NULL) {
- log_error1("url is NULL!");
- return ;
- }
+ if (url == NULL) {
+ log_error1("url is NULL!");
+ return ;
+ }
- log_verbose2("PROTOCOL : %s", SAVE_STR(url->protocol));
- log_verbose2(" HOST : %s", SAVE_STR(url->host));
- log_verbose2(" PORT : %d", url->port);
- log_verbose2(" CONTEXT : %s", SAVE_STR(url->context));
+ log_verbose2("PROTOCOL : %s", SAVE_STR(url->protocol));
+ log_verbose2(" HOST : %s", SAVE_STR(url->host));
+ log_verbose2(" PORT : %d", url->port);
+ log_verbose2(" CONTEXT : %s", SAVE_STR(url->context));
}
hurl_t* hurl_new(const char* urlstr)
{
- int iprotocol;
- int ihost;
- int iport;
- int len;
- int size;
- hurl_t *url;
- char tmp[8];
-
- iprotocol = 0;
- len = strlen(urlstr);
-
- /* find protocol */
- while (urlstr[iprotocol] != ':' && urlstr[iprotocol] != '\0')
- {
- iprotocol++;
- }
-
- if (iprotocol == 0) {
- log_error1("no protocol");
- return NULL;
- }
-
- if (iprotocol + 3 >= len) {
- log_error1("no host");
- return NULL;
- }
-
- if ( urlstr[iprotocol] != ':'
- && urlstr[iprotocol+1] != '/'
- && urlstr[iprotocol+2] != '/')
- {
- log_error1("no protocol");
- return NULL;
- }
-
- /* find host */
- ihost = iprotocol + 3;
- while (urlstr[ihost] != ':'
- && urlstr[ihost] != '/'
- && urlstr[ihost] != '\0')
- {
- ihost++;
- }
-
- if (ihost == iprotocol + 1) {
- log_error1("no host");
- return NULL;
- }
-
- /* find port */
- iport = ihost;
- if (ihost + 1 < len) {
- if (urlstr[ihost] == ':') {
- while (urlstr[iport] != '/' && urlstr[iport] != '\0') {
- iport++;
- }
- }
- }
-
- url = (hurl_t*)malloc(sizeof(hurl_t));
-
- url->protocol = (char*)malloc(sizeof(char)*iprotocol+1);
- strncpy(url->protocol, urlstr, iprotocol);
- url->protocol[iprotocol] = '\0';
-
- size = ihost - iprotocol - 3;
- url->host = (char*)malloc(sizeof(char)*size + 1);
- strncpy(url->host, &urlstr[iprotocol+3], size);
- url->host[size] = '\0';
-
- if (iport > ihost)
- {
- size = iport - ihost;
- strncpy(tmp, &urlstr[ihost+1], size);
- url->port = atoi(tmp);
- } else {
- url->port = 80;
- }
-
- len = strlen(urlstr);
- if (len > iport )
- {
- size = len - iport;
- url->context = (char*)malloc(sizeof(char)*size+1);
- strncpy(url->context, &urlstr[iport], size);
- url->context[size]='\0';
- } else {
- url->context = NULL;
- }
-
- hurl_dump(url);
-
- return url;
+ int iprotocol;
+ int ihost;
+ int iport;
+ int len;
+ int size;
+ hurl_t *url;
+ char tmp[8];
+
+ iprotocol = 0;
+ len = strlen(urlstr);
+
+ /* find protocol */
+ while (urlstr[iprotocol] != ':' && urlstr[iprotocol] != '\0')
+ {
+ iprotocol++;
+ }
+
+ if (iprotocol == 0) {
+ log_error1("no protocol");
+ return NULL;
+ }
+
+ if (iprotocol + 3 >= len) {
+ log_error1("no host");
+ return NULL;
+ }
+
+ if ( urlstr[iprotocol] != ':'
+ && urlstr[iprotocol+1] != '/'
+ && urlstr[iprotocol+2] != '/')
+ {
+ log_error1("no protocol");
+ return NULL;
+ }
+
+ /* find host */
+ ihost = iprotocol + 3;
+ while (urlstr[ihost] != ':'
+ && urlstr[ihost] != '/'
+ && urlstr[ihost] != '\0')
+ {
+ ihost++;
+ }
+
+ if (ihost == iprotocol + 1) {
+ log_error1("no host");
+ return NULL;
+ }
+
+ /* find port */
+ iport = ihost;
+ if (ihost + 1 < len) {
+ if (urlstr[ihost] == ':') {
+ while (urlstr[iport] != '/' && urlstr[iport] != '\0') {
+ iport++;
+ }
+ }
+ }
+
+ url = (hurl_t*)malloc(sizeof(hurl_t));
+
+ url->protocol = (char*)malloc(sizeof(char)*iprotocol+1);
+ strncpy(url->protocol, urlstr, iprotocol);
+ url->protocol[iprotocol] = '\0';
+
+ size = ihost - iprotocol - 3;
+ url->host = (char*)malloc(sizeof(char)*size + 1);
+ strncpy(url->host, &urlstr[iprotocol+3], size);
+ url->host[size] = '\0';
+
+ if (iport > ihost)
+ {
+ size = iport - ihost;
+ strncpy(tmp, &urlstr[ihost+1], size);
+ url->port = atoi(tmp);
+ } else {
+ url->port = 80;
+ }
+
+ len = strlen(urlstr);
+ if (len > iport )
+ {
+ size = len - iport;
+ url->context = (char*)malloc(sizeof(char)*size+1);
+ strncpy(url->context, &urlstr[iport], size);
+ url->context[size]='\0';
+ } else {
+ url->context = NULL;
+ }
+
+ hurl_dump(url);
+
+ return url;
}
void hurl_free(hurl_t *url)
{
- if (url == NULL) return;
+ if (url == NULL) return;
- free(url->protocol);
- free(url->host);
- free(url->context);
+ free(url->protocol);
+ free(url->host);
+ free(url->context);
- free(url);
+ free(url);
}
/* request stuff */
/* -----------------------------------------------------
- FUNCTION: hrequest_new_from_buffer
+FUNCTION: hrequest_new_from_buffer
----------------------------------------------------- */
hrequest_t *hrequest_new_from_buffer(char *data)
{
- hrequest_t *req;
- hpair_t *hpair = NULL, *qpair = NULL, *tmppair = NULL;
-
- char *tmp;
- char *tmp2;
- char *saveptr;
- char *saveptr2;
- char *saveptr3;
- char *result;
- char *key;
- char *value;
- char *opt_key;
- char *opt_value;
- int firstline = 1;
-
- req = (hrequest_t*)malloc(sizeof(hrequest_t));
-
- req->method = NULL;
- req->spec = NULL;
- req->path = NULL;
- req->query = NULL;
- req->header = NULL;
-
- tmp = data;
-
- for (;;) {
- result = (char*)strtok_r(tmp, "\n", &saveptr);
- tmp=saveptr;
-
- if (result == NULL)
- break;
-
- if (firstline) {
- firstline=0;
- tmp2 = result;
-
- /* parse [GET|POST] [PATH] [SPEC] */
- key = (char*)strtok_r(tmp2," ", &saveptr2);
-
- /* save method (get or post) */
- tmp2 = saveptr2;
- if (key != NULL) {
- req->method = (char*)malloc(strlen(key)+1);
- strcpy(req->method, key);
- }
-
- /* below is key the path and tmp2 the spec */
- key = (char*)strtok_r(tmp2," ", &saveptr2);
-
- /* save spec */
- tmp2 = saveptr2;
- if (tmp2 != NULL) {
- req->spec = (char*)malloc(strlen(tmp2)+1);
- strcpy(req->spec, tmp2);
- }
-
- /* parse and save path+query
- parse: /path/of/target?key1=value1&key2=value2...
- */
-
- if (key != NULL) {
- tmp2 = key;
- key = (char*)strtok_r(tmp2,"?", &saveptr2);
- tmp2 = saveptr2;
-
- /* save path */
- req->path = (char*)malloc(strlen(key)+1);
- strcpy(req->path, key);
-
- /* parse options */
- for (;;) {
- key = (char*)strtok_r(tmp2,"&",&saveptr2);
- tmp2 = saveptr2;
-
- if (key == NULL)
- break;
-
- opt_key = (char*)strtok_r(key,"=", &saveptr3);
- opt_value = saveptr3;
-
- if (opt_value == NULL)
- opt_value = "";
-
- /* create option pair */
- if (opt_key != NULL) {
- tmppair = (hpair_t*)malloc(sizeof(hpair_t));
-
- if (req->query == NULL) {
- req->query = qpair = tmppair;
- } else {
- qpair->next = tmppair;
- qpair = tmppair;
- }
-
- /* fill hpairnode_t struct */
- qpair->next = NULL;
- qpair->key = (char*)malloc(strlen(opt_key)+1);
- qpair->value = (char*)malloc(strlen(opt_value)+1);
-
- strcpy(qpair->key, opt_key);
- strcpy(qpair->value, opt_value);
-
- }
+ hrequest_t *req;
+ hpair_t *hpair = NULL, *qpair = NULL, *tmppair = NULL;
+
+ char *tmp;
+ char *tmp2;
+ char *saveptr;
+ char *saveptr2;
+ char *saveptr3;
+ char *result;
+ char *key;
+ char *value;
+ char *opt_key;
+ char *opt_value;
+ int firstline = 1;
+
+ req = (hrequest_t*)malloc(sizeof(hrequest_t));
+
+ req->method = NULL;
+ req->spec = NULL;
+ req->path = NULL;
+ req->query = NULL;
+ req->header = NULL;
+
+ tmp = data;
+
+ for (;;) {
+ result = (char*)strtok_r(tmp, "\n", &saveptr);
+ tmp=saveptr;
+
+ if (result == NULL)
+ break;
+
+ if (firstline) {
+ firstline=0;
+ tmp2 = result;
+
+ /* parse [GET|POST] [PATH] [SPEC] */
+ key = (char*)strtok_r(tmp2," ", &saveptr2);
+
+ /* save method (get or post) */
+ tmp2 = saveptr2;
+ if (key != NULL) {
+ req->method = (char*)malloc(strlen(key)+1);
+ strcpy(req->method, key);
+ }
+
+ /* below is key the path and tmp2 the spec */
+ key = (char*)strtok_r(tmp2," ", &saveptr2);
+
+ /* save spec */
+ tmp2 = saveptr2;
+ if (tmp2 != NULL) {
+ req->spec = (char*)malloc(strlen(tmp2)+1);
+ strcpy(req->spec, tmp2);
+ }
+
+ /* parse and save path+query
+ parse: /path/of/target?key1=value1&key2=value2...
+ */
+
+ if (key != NULL) {
+ tmp2 = key;
+ key = (char*)strtok_r(tmp2,"?", &saveptr2);
+ tmp2 = saveptr2;
+
+ /* save path */
+ req->path = (char*)malloc(strlen(key)+1);
+ strcpy(req->path, key);
+
+ /* parse options */
+ for (;;) {
+ key = (char*)strtok_r(tmp2,"&",&saveptr2);
+ tmp2 = saveptr2;
+
+ if (key == NULL)
+ break;
+
+ opt_key = (char*)strtok_r(key,"=", &saveptr3);
+ opt_value = saveptr3;
+
+ if (opt_value == NULL)
+ opt_value = "";
+
+ /* create option pair */
+ if (opt_key != NULL) {
+ tmppair = (hpair_t*)malloc(sizeof(hpair_t));
+
+ if (req->query == NULL) {
+ req->query = qpair = tmppair;
+ } else {
+ qpair->next = tmppair;
+ qpair = tmppair;
+ }
+
+ /* fill hpairnode_t struct */
+ qpair->next = NULL;
+ qpair->key = (char*)malloc(strlen(opt_key)+1);
+ qpair->value = (char*)malloc(strlen(opt_value)+1);
+
+ strcpy(qpair->key, opt_key);
+ strcpy(qpair->value, opt_value);
+
+ }
+ }
+ }
+
+ } else {
+
+ /* parse "key: value" */
+ tmp2 = result;
+ key = (char*)strtok_r(tmp2, ": ", &saveptr2);
+ value = saveptr2;
+
+ /* create pair */
+ tmppair = (hpair_t*)malloc(sizeof(hpair_t));
+
+ if (req->header == NULL) {
+ req->header = hpair = tmppair;
+ } else {
+ hpair->next = tmppair;
+ hpair = tmppair;
+ }
+
+ /* fill pairnode_t struct */
+ hpair->next = NULL;
+ hpair->key = (char*)malloc(strlen(key)+1);
+ hpair->value = (char*)malloc(strlen(value)+1);
+
+ strcpy(hpair->key, key);
+ strcpy(hpair->value, value);
+ }
}
- }
-
- } else {
-
- /* parse "key: value" */
- tmp2 = result;
- key = (char*)strtok_r(tmp2, ": ", &saveptr2);
- value = saveptr2;
-
- /* create pair */
- tmppair = (hpair_t*)malloc(sizeof(hpair_t));
-
- if (req->header == NULL) {
- req->header = hpair = tmppair;
- } else {
- hpair->next = tmppair;
- hpair = tmppair;
- }
-
- /* fill pairnode_t struct */
- hpair->next = NULL;
- hpair->key = (char*)malloc(strlen(key)+1);
- hpair->value = (char*)malloc(strlen(value)+1);
-
- strcpy(hpair->key, key);
- strcpy(hpair->value, value);
- }
- }
-
- return req;
+
+ return req;
}
void hrequest_free(hrequest_t *req)
{
- if (req == NULL) return;
+ if (req == NULL) return;
- free(req->method);
- free(req->path);
- free(req->spec);
+ free(req->method);
+ free(req->path);
+ free(req->spec);
+
+ hpairnode_free_deep(req->header);
+ hpairnode_free_deep(req->query);
- hpairnode_free_deep(req->header);
- hpairnode_free_deep(req->query);
-
}
/* response stuff */
/* -------------------------------------------
- FUNCTION: hresponse_new
- ---------------------------------------------*/
+FUNCTION: hresponse_new
+---------------------------------------------*/
hresponse_t *hresponse_new()
{
- hresponse_t *res;
-
- /* create response object */
- res = (hresponse_t*)malloc(sizeof(hresponse_t));
- res->spec[0] = '\0';
- res->errcode = -1;
- res->desc = NULL;
- res->header = NULL;
- res->body = NULL;
- res->bodysize = 0;
-
- return res;
+ hresponse_t *res;
+
+ /* create response object */
+ res = (hresponse_t*)malloc(sizeof(hresponse_t));
+ res->spec[0] = '\0';
+ res->errcode = -1;
+ res->desc = NULL;
+ res->header = NULL;
+ res->body = NULL;
+ res->bodysize = 0;
+
+ return res;
}
/* -------------------------------------------
- FUNCTION: hresponse_new_from_buffer
- ---------------------------------------------*/
+FUNCTION: hresponse_new_from_buffer
+---------------------------------------------*/
hresponse_t *hresponse_new_from_buffer(const char* buffer)
{
- hresponse_t *res;
- char *s1, *s2, *str;
- hpair_t *pair;
-
- /* create response object */
- res = hresponse_new();
-
- /* *** parse spec *** */
- /* [HTTP/1.1 | 1.2] [CODE] [DESC] */
-
- /* stage 1: HTTP spec */
- str = (char*)strtok_r(buffer, " ", &s2);
- s1 = s2;
- if (str == NULL) { log_error1("Parse error"); return NULL; }
-
- strncpy(res->spec, str, 10);
-
- /* stage 2: http code */
- str = (char*)strtok_r(s1, " ", &s2);
- s1 = s2;
- if (str == NULL) { log_error1("Parse error"); return NULL; }
-
- res->errcode = atoi(str);
-
- /* stage 3: description text */
- str = (char*)strtok_r(s1, "\r\n", &s2);
- s1 = s2;
- if (str == NULL) { log_error1("Parse error"); return NULL; }
-
- res->desc = (char*)malloc(strlen(str)+1);
- strcpy(res->desc, str);
- res->desc[strlen(str)] = '\0';
-
- /* *** parse header *** */
- /* [key]: [value] */
- for (;;) {
- str = strtok_r(s1, "\n", &s2);
- s1 = s2;
-
- /* check if header ends without body */
- if (str == NULL) {
- return res;
- }
-
- /* check also for end of header */
- if (!strcmp(str, "\r")) {
- break;
- }
-
- str[strlen(str)-1] = '\0';
- res->header = hpairnode_parse(str, ":", res->header);
- }
-
- /* *** Save body *** */
- res->body = s1;
-
- /* return response object */
- return res;
-}
+ hresponse_t *res;
+ char *s1, *s2, *str;
+ hpair_t *pair;
+ /* create response object */
+ res = hresponse_new();
-void hresponse_free(hresponse_t *res)
-{
- /* not implemented yet!*/
-}
+ /* *** parse spec *** */
+ /* [HTTP/1.1 | 1.2] [CODE] [DESC] */
+
+ /* stage 1: HTTP spec */
+ str = (char*)strtok_r((char *)buffer, " ", &s2);
+ s1 = s2;
+ if (str == NULL) { log_error1("Parse error"); return NULL; }
+
+ strncpy(res->spec, str, 10);
+ /* stage 2: http code */
+ str = (char*)strtok_r(s1, " ", &s2);
+ s1 = s2;
+ if (str == NULL) { log_error1("Parse error"); return NULL; }
+ res->errcode = atoi(str);
+ /* stage 3: description text */
+ str = (char*)strtok_r(s1, "\r\n", &s2);
+ s1 = s2;
+ if (str == NULL) { log_error1("Parse error"); return NULL; }
+ res->desc = (char*)malloc(strlen(str)+1);
+ strcpy(res->desc, str);
+ res->desc[strlen(str)] = '\0';
+ /* *** parse header *** */
+ /* [key]: [value] */
+ for (;;) {
+ str = strtok_r(s1, "\n", &s2);
+ s1 = s2;
+ /* check if header ends without body */
+ if (str == NULL) {
+ return res;
+ }
+ /* check also for end of header */
+ if (!strcmp(str, "\r")) {
+ break;
+ }
+ str[strlen(str)-1] = '\0';
+ res->header = hpairnode_parse(str, ":", res->header);
+ }
+
+ /* *** Save body *** */
+ res->body = s1;
+
+ /* return response object */
+ return res;
+}
+
+
+void hresponse_free(hresponse_t *res)
+{
+ /* not implemented yet!*/
+}