summaryrefslogtreecommitdiffstats
path: root/nanohttp
diff options
context:
space:
mode:
Diffstat (limited to 'nanohttp')
-rw-r--r--nanohttp/nanohttp-client.c8
-rw-r--r--nanohttp/nanohttp-client.h10
-rw-r--r--nanohttp/nanohttp-common.c4
-rw-r--r--nanohttp/nanohttp-common.h30
-rwxr-xr-xnanohttp/nanohttp-mime.c4
-rwxr-xr-xnanohttp/nanohttp-mime.h10
-rwxr-xr-xnanohttp/nanohttp-request.c38
-rwxr-xr-xnanohttp/nanohttp-request.h10
-rwxr-xr-xnanohttp/nanohttp-response.c21
-rwxr-xr-xnanohttp/nanohttp-response.h10
-rw-r--r--nanohttp/nanohttp-server.c244
-rw-r--r--nanohttp/nanohttp-server.h10
-rw-r--r--nanohttp/nanohttp-socket.c73
-rw-r--r--nanohttp/nanohttp-socket.h17
-rw-r--r--nanohttp/nanohttp-ssl.h8
-rwxr-xr-xnanohttp/nanohttp-stream.c83
-rwxr-xr-xnanohttp/nanohttp-stream.h15
17 files changed, 336 insertions, 259 deletions
diff --git a/nanohttp/nanohttp-client.c b/nanohttp/nanohttp-client.c
index 802e021..09605b9 100644
--- a/nanohttp/nanohttp-client.c
+++ b/nanohttp/nanohttp-client.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-client.c,v 1.38 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-client.c,v 1.39 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -147,7 +147,7 @@ httpc_close_free(httpc_conn_t * conn)
if (conn == NULL)
return;
- hsocket_close(conn->sock);
+ hsocket_close(&(conn->sock));
httpc_free(conn);
return;
@@ -363,7 +363,7 @@ httpc_talk_to_server(hreq_method_t method, httpc_conn_t * conn,
if ((status = hsocket_send(conn->sock, buffer)) != H_OK)
{
log_error2("Can not send request (status:%d)", status);
- hsocket_close(conn->sock);
+ hsocket_close(&(conn->sock));
return status;
}
@@ -371,7 +371,7 @@ httpc_talk_to_server(hreq_method_t method, httpc_conn_t * conn,
if ((status = httpc_send_header(conn)) != H_OK)
{
log_error2("Can not send header (status:%d)", status);
- hsocket_close(conn->sock);
+ hsocket_close(&(conn->sock));
return status;
}
diff --git a/nanohttp/nanohttp-client.h b/nanohttp/nanohttp-client.h
index d77f80f..5562ea6 100644
--- a/nanohttp/nanohttp-client.h
+++ b/nanohttp/nanohttp-client.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-client.h,v 1.21 2006/02/27 00:00:14 snowdrop Exp $
+ * $Id: nanohttp-client.h,v 1.22 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -24,10 +24,6 @@
#ifndef NANO_HTTP_CLIENT_H
#define NANO_HTTP_CLIENT_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <nanohttp/nanohttp-common.h>
#include <nanohttp/nanohttp-socket.h>
#include <nanohttp/nanohttp-response.h>
@@ -50,6 +46,10 @@ typedef struct httpc_conn
} httpc_conn_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+
/* --------------------------------------------------------------
HTTP CLIENT MODULE RELATED FUNCTIONS
---------------------------------------------------------------*/
diff --git a/nanohttp/nanohttp-common.c b/nanohttp/nanohttp-common.c
index 1f2040d..f49cc85 100644
--- a/nanohttp/nanohttp-common.c
+++ b/nanohttp/nanohttp-common.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-common.c,v 1.27 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-common.c,v 1.28 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -53,7 +53,7 @@
#include <utils/alloc.h>
#endif
-#include <nanohttp/nanohttp-common.h>
+#include "nanohttp-common.h"
#define MAX_OPTION_SIZE 50
#define MAX_OPTION_VALUE_SIZE 150
diff --git a/nanohttp/nanohttp-common.h b/nanohttp/nanohttp-common.h
index 736f84c..307f349 100644
--- a/nanohttp/nanohttp-common.h
+++ b/nanohttp/nanohttp-common.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-common.h,v 1.26 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-common.h,v 1.27 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -24,10 +24,6 @@
#ifndef NANO_HTTP_COMMON_H
#define NANO_HTTP_COMMON_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <stdlib.h>
#include <time.h>
@@ -157,17 +153,6 @@ Set Sleep function platform depended
#define system_sleep(seconds) sleep(seconds);
#endif
-#ifdef WIN32
-#include <string.h>
-char *strtok_r(char *s, const char *delim, char **save_ptr);
-struct tm *localtime_r(const time_t * const timep, struct tm *p_tm);
-#endif
-
-typedef unsigned char byte_t;
-typedef void *herror_t;
-
-
-
/**
Indicates the version of the
used HTTP protocol.
@@ -189,6 +174,19 @@ typedef enum _hreq_method
} hreq_method_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#ifdef WIN32
+#include <string.h>
+char *strtok_r(char *s, const char *delim, char **save_ptr);
+struct tm *localtime_r(const time_t * const timep, struct tm *p_tm);
+#endif
+
+typedef unsigned char byte_t;
+typedef void *herror_t;
+
herror_t herror_new(const char *func, int errcode, const char *format, ...);
int herror_code(herror_t err);
char *herror_func(herror_t err);
diff --git a/nanohttp/nanohttp-mime.c b/nanohttp/nanohttp-mime.c
index 10926fe..5ab5592 100755
--- a/nanohttp/nanohttp-mime.c
+++ b/nanohttp/nanohttp-mime.c
@@ -3,7 +3,7 @@
* | \/ | | | | \/ | | _/
* |_''_| |_| |_''_| |_'/ PARSER
*
-* $Id: nanohttp-mime.c,v 1.10 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-mime.c,v 1.11 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -45,7 +45,7 @@ Buffered Reader. A helper object to read bytes from a source
#include <utils/alloc.h>
#endif
-#include <nanohttp/nanohttp-mime.h>
+#include "nanohttp-mime.h"
/* ------------------------------------------------------------------
diff --git a/nanohttp/nanohttp-mime.h b/nanohttp/nanohttp-mime.h
index bf3c8c0..f63535a 100755
--- a/nanohttp/nanohttp-mime.h
+++ b/nanohttp/nanohttp-mime.h
@@ -3,7 +3,7 @@
* | \/ | | | | \/ | | _/
* |_''_| |_| |_''_| |_'/ PARSER
*
-* $Id: nanohttp-mime.h,v 1.7 2006/02/27 00:26:23 snowdrop Exp $
+* $Id: nanohttp-mime.h,v 1.8 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -29,14 +29,12 @@
#ifndef NANO_HTTP_MIME_PARSER_H
#define NANO_HTTP_MIME_PARSER_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <nanohttp/nanohttp-common.h>
#include <nanohttp/nanohttp-stream.h>
-#include <stdlib.h>
+#ifdef __cplusplus
+extern "C" {
+#endif
/* ------------------------------------------------------------------
"multipart/related" MIME Message Builder
diff --git a/nanohttp/nanohttp-request.c b/nanohttp/nanohttp-request.c
index 98880f2..1a3e998 100755
--- a/nanohttp/nanohttp-request.c
+++ b/nanohttp/nanohttp-request.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-request.c,v 1.10 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-request.c,v 1.11 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -25,24 +25,35 @@
#include <config.h>
#endif
+#ifdef HAVE_STDIO_H
+#include <stdio.h>
+#endif
+
#ifdef HAVE_STRING_H
#include <string.h>
#endif
+#ifdef HAVE_ERRNO_H
+#include <errno.h>
+#endif
+
#ifdef MEM_DEBUG
#include <utils/alloc.h>
#endif
-#include <nanohttp/nanohttp-common.h>
-#include <nanohttp/nanohttp-request.h>
-
-/* request stuff */
-
+#include "nanohttp-common.h"
+#include "nanohttp-request.h"
static hrequest_t *
hrequest_new()
{
- hrequest_t *req = (hrequest_t *) malloc(sizeof(hrequest_t));
+ hrequest_t *req;
+
+ if (!(req = (hrequest_t *) malloc(sizeof(hrequest_t)))) {
+
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
req->method = HTTP_REQUEST_GET;
req->version = HTTP_1_1;
@@ -147,7 +158,11 @@ _hrequest_parse_header(char *data)
/* create option pair */
if (opt_key != NULL)
{
- tmppair = (hpair_t *) malloc(sizeof(hpair_t));
+ if (!(tmppair = (hpair_t *) malloc(sizeof(hpair_t))))
+ {
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
if (req->query == NULL)
{
@@ -161,11 +176,8 @@ _hrequest_parse_header(char *data)
/* 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);
+ qpair->key = strdup(opt_key);
+ qpair->value = strdup(opt_value);
}
}
diff --git a/nanohttp/nanohttp-request.h b/nanohttp/nanohttp-request.h
index d89fa91..c0c014c 100755
--- a/nanohttp/nanohttp-request.h
+++ b/nanohttp/nanohttp-request.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-request.h,v 1.5 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-request.h,v 1.6 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -24,10 +24,6 @@
#ifndef NANO_HTTP_REQUEST_H
#define NANO_HTTP_REQUEST_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <nanohttp/nanohttp-stream.h>
#include <nanohttp/nanohttp-mime.h>
@@ -49,6 +45,10 @@ typedef struct hrequest
char root_part_id[150];
} hrequest_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+
herror_t hrequest_new_from_socket(hsocket_t sock, hrequest_t ** out);
void hrequest_free(hrequest_t * req);
diff --git a/nanohttp/nanohttp-response.c b/nanohttp/nanohttp-response.c
index cf728e4..64eac44 100755
--- a/nanohttp/nanohttp-response.c
+++ b/nanohttp/nanohttp-response.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-response.c,v 1.8 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-response.c,v 1.9 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -25,16 +25,24 @@
#include <config.h>
#endif
+#ifdef HAVE_STDIO_H
+#include <stdio.h>
+#endif
+
#ifdef HAVE_STRING_H
#include <string.h>
#endif
+#ifdef HAVE_ERRNO_H
+#include <errno.h>
+#endif
+
#ifdef MEM_DEBUG
#include <utils/alloc.h>
#endif
-#include <nanohttp/nanohttp-common.h>
-#include <nanohttp/nanohttp-response.h>
+#include "nanohttp-common.h"
+#include "nanohttp-response.h"
static hresponse_t *
hresponse_new()
@@ -42,7 +50,12 @@ hresponse_new()
hresponse_t *res;
/* create response object */
- res = (hresponse_t *) malloc(sizeof(hresponse_t));
+ if (!(res = (hresponse_t *) malloc(sizeof(hresponse_t)))) {
+
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
+
res->version = HTTP_1_1;
res->errcode = -1;
res->desc[0] = '\0';
diff --git a/nanohttp/nanohttp-response.h b/nanohttp/nanohttp-response.h
index bd7bb50..3b3f532 100755
--- a/nanohttp/nanohttp-response.h
+++ b/nanohttp/nanohttp-response.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-response.h,v 1.5 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-response.h,v 1.6 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -24,10 +24,6 @@
#ifndef NANO_HTTP_RESPONSE_H
#define NANO_HTTP_RESPONSE_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <nanohttp/nanohttp-stream.h>
#include <nanohttp/nanohttp-common.h>
#include <nanohttp/nanohttp-mime.h>
@@ -47,6 +43,10 @@ typedef struct hresponse
char root_part_id[150];
} hresponse_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+
herror_t hresponse_new_from_socket(hsocket_t sock, hresponse_t ** out);
void hresponse_free(hresponse_t * res);
diff --git a/nanohttp/nanohttp-server.c b/nanohttp/nanohttp-server.c
index c885a72..d60c797 100644
--- a/nanohttp/nanohttp-server.c
+++ b/nanohttp/nanohttp-server.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-server.c,v 1.50 2006/02/21 16:40:47 mrcsys Exp $
+* $Id: nanohttp-server.c,v 1.51 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -29,6 +29,10 @@
#include <sys/select.h>
#endif
+#ifdef HAVE_SOCKET_H
+#include <sys/socket.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
#endif
@@ -57,17 +61,16 @@
#include <unistd.h>
#endif
-#ifdef HAVE_PTHREAD_H
-#include <pthread.h>
+#ifdef HAVE_ERRNO_H
+#include <errno.h>
#endif
-#ifdef HAVE_SOCKET_H
-#include <sys/socket.h>
+#ifdef HAVE_PTHREAD_H
+#include <pthread.h>
#endif
-#ifdef WIN32
+#ifdef HAVE_PROCESS_H
#include <process.h>
-#define snprintf(buffer, num, s1, s2) sprintf(buffer, s1,s2)
#endif
#ifdef MEM_DEBUG
@@ -97,13 +100,15 @@ conndata_t;
* internally globals
* -----------------------------------------------------
*/
+static volatile int _httpd_run = 1;
+
+static hsocket_t _httpd_socket;
static int _httpd_port = 10000;
static int _httpd_max_connections = 20;
-static hsocket_t _httpd_socket;
+
static hservice_t *_httpd_services_default = NULL;
static hservice_t *_httpd_services_head = NULL;
static hservice_t *_httpd_services_tail = NULL;
-static int _httpd_run = 1;
static conndata_t *_httpd_connection;
#ifdef WIN32
@@ -111,15 +116,42 @@ static DWORD _httpd_terminate_signal = CTRL_C_EVENT;
static int _httpd_max_idle = 120;
static void WSAReaper (void *x);
#define strncasecmp(s1, s2, num) strncmp(s1, s2, num)
+#define snprintf(buffer, num, s1, s2) sprintf(buffer, s1,s2)
#else
static int _httpd_terminate_signal = SIGINT;
static sigset_t thrsigset;
#endif
-#ifdef HAVE_SSL
-/*extern SSL_CTX *SSLctx;*/
-#endif
+static void
+_httpd_parse_arguments(int argc, char **argv)
+{
+ int i;
+ /* write argument information */
+ log_verbose1 ("Arguments:");
+ for (i = 0; i < argc; i++)
+ log_verbose3 ("argv[%i] = '%s'", i, SAVE_STR (argv[i]));
+
+ for (i = 1; i < argc; i++)
+ {
+ if (!strcmp (argv[i-1], NHTTPD_ARG_PORT))
+ {
+ _httpd_port = atoi (argv[i]);
+ }
+ else if (!strcmp (argv[i-1], NHTTPD_ARG_TERMSIG))
+ {
+ _httpd_terminate_signal = atoi (argv[i]);
+ }
+ else if (!strcmp (argv[i-1], NHTTPD_ARG_MAXCONN))
+ {
+ _httpd_max_connections = atoi (argv[i]);
+ }
+ }
+
+ log_verbose2 ("socket bind to port '%d'", _httpd_port);
+
+ return;
+}
/*
* -----------------------------------------------------
@@ -136,33 +168,14 @@ httpd_init (int argc, char *argv[])
char *SSLCert = NULL, *SSLPass = NULL, *SSLCA = NULL;
#endif
+ /* XXX: two times argument parsing... */
hoption_init_args (argc, argv);
+ _httpd_parse_arguments(argc, argv);
+
if ((status = hsocket_module_init()) != H_OK)
return status;
- /* write argument information */
- log_verbose1 ("Arguments:");
- for (i = 0; i < argc; i++)
- log_verbose3 ("argv[%i] = '%s'", i, SAVE_STR (argv[i]));
-
- /* initialize from arguments */
- for (i = 0; i < argc; i++)
- {
- if (!strcmp (argv[i], NHTTPD_ARG_PORT) && i < argc - 1)
- {
- _httpd_port = atoi (argv[i + 1]);
- }
- else if (!strcmp (argv[i], NHTTPD_ARG_TERMSIG) && i < argc - 1)
- {
- _httpd_terminate_signal = atoi (argv[i + 1]);
- }
- else if (!strcmp (argv[i], NHTTPD_ARG_MAXCONN) && i < argc - 1)
- {
- _httpd_max_connections = atoi (argv[i + 1]);
- }
- }
-
log_verbose2 ("socket bind to port '%d'", _httpd_port);
/* init built-in services */
@@ -171,9 +184,7 @@ httpd_init (int argc, char *argv[])
_httpd_connection = calloc (_httpd_max_connections, sizeof (conndata_t));
for (i = 0; i < _httpd_max_connections; i++)
- {
- memset ((char *) &_httpd_connection[i], 0, sizeof (_httpd_connection[i]));
- }
+ hsocket_init(&(_httpd_connection[i].sock));
#ifdef WIN32
/*
@@ -183,7 +194,7 @@ httpd_init (int argc, char *argv[])
*/
#endif
- /* create socket */
+ /* XXX: move SSL stuff to nanohttp-socket.c and handle this transparently */
#ifdef HAVE_SSL
SSLCert = hoption_get(HOPTION_SSL_CERT);
SSLPass = hoption_get(HOPTION_SSL_PASS);
@@ -221,7 +232,7 @@ httpd_register_secure(const char *ctx, httpd_service func, httpd_auth auth)
if (!(service = (hservice_t *) malloc (sizeof (hservice_t))))
{
- log_error1("malloc failed");
+ log_error2("malloc failed (%s)", strerror(errno));
return -1;
}
@@ -396,10 +407,13 @@ httpd_send_internal_error (httpd_conn_t * conn, const char *errmsg)
char buffer[4064];
char buflen[5];
+
sprintf (buffer, template1, errmsg);
snprintf (buflen, 5, "%d", strlen (buffer));
+
httpd_set_header (conn, HEADER_CONTENT_LENGTH, buflen);
httpd_send_header (conn, 500, "INTERNAL");
+
return hsocket_nsend (conn->sock, buffer, strlen (buffer));
}
@@ -421,28 +435,29 @@ httpd_request_print (hrequest_t * req)
(req->version == HTTP_1_0) ? "HTTP/1.0" : "HTTP/1.1");
log_verbose1 (" Parsed query string :");
- pair = req->query;
- while (pair != NULL)
- {
+ for (pair = req->query; pair; pair = pair->next)
log_verbose3 (" %s = '%s'", pair->key, pair->value);
- pair = pair->next;
- }
+
log_verbose1 (" Parsed header :");
- pair = req->header;
- while (pair != NULL)
- {
+ for (pair = req->header; pair; pair = pair->next)
log_verbose3 (" %s = '%s'", pair->key, pair->value);
- pair = pair->next;
- }
+
log_verbose1 ("++++++++++++++++++++++++");
+ return;
}
httpd_conn_t *
httpd_new (hsocket_t sock)
{
- httpd_conn_t *conn = (httpd_conn_t *) malloc (sizeof (httpd_conn_t));
+ httpd_conn_t *conn;
+
+ if (!(conn = (httpd_conn_t *) malloc (sizeof (httpd_conn_t)))) {
+
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
conn->sock = sock;
conn->out = NULL;
conn->content_type[0] = '\0';
@@ -455,15 +470,18 @@ httpd_new (hsocket_t sock)
void
httpd_free (httpd_conn_t * conn)
{
- if(!conn)
- return;
- if (conn->out != NULL)
+ if (!conn)
+ return;
+
+ if (conn->out)
http_output_stream_free (conn->out);
- if (conn->header != NULL)
+ if (conn->header)
hpairnode_free_deep (conn->header);
free (conn);
+
+ return;
}
void
@@ -485,44 +503,44 @@ do_req_timeout (int signum)
#endif
}
-static int httpd_decode_authorization(const char *value, char **user, char **pass)
+static int _httpd_decode_authorization(const char *value, char **user, char **pass)
{
unsigned char *tmp, *tmp2;
+ size_t len;
- tmp = malloc(strlen(value) * 2);
-#ifdef WIN32
- memset(tmp, 0, strlen(value)*2);
- value = strstr(value, ' ');
-#else
- bzero(tmp, strlen(value) * 2);
- value = index(value, ' ');
-#endif
+ len = strlen(value) * 2;
+ if (!(tmp = (char *)calloc(1, len))) {
+
+ log_error2("malloc failed (%s)", strerror(errno));
+ return -1;
+ }
+ value = strstr(value, " ") + 1;
- value++;
- log_debug2("Authorization (base64) = \"%s\"", value);
+ log_error2("Authorization (base64) = \"%s\"", value);
base64_decode(value, tmp);
- log_debug2("Authorization (ascii) = \"%s\"", tmp);
+ log_error2("Authorization (ascii) = \"%s\"", tmp);
-#ifdef WIN32
- tmp2 = strstr(tmp, ':');
-#else
- tmp2 = index(tmp, ':');
-#endif
- *tmp2++ = '\0';
-
- *pass = strdup(tmp2);
+ if ((tmp2 = strstr(tmp, ":")))
+ {
+ *tmp2++ = '\0';
+ *pass = strdup(tmp2);
+ }
+ else
+ {
+ *pass = strdup("");
+ }
*user = strdup(tmp);
free(tmp);
- return 1;
+ return 0;
}
-static int httpd_authenticate_request(hrequest_t *req, httpd_auth auth)
+static int _httpd_authenticate_request(hrequest_t *req, httpd_auth auth)
{
char *user, *pass;
char *authorization;
@@ -532,17 +550,20 @@ static int httpd_authenticate_request(hrequest_t *req, httpd_auth auth)
return 1;
if (!(authorization = hpairnode_get_ignore_case(req->header, HEADER_AUTHORIZATION))) {
+ log_debug2("%s header not set", HEADER_AUTHORIZATION);
return 0;
}
- if (!httpd_decode_authorization(authorization, &user, &pass))
+ if (_httpd_decode_authorization(authorization, &user, &pass))
{
log_error1("httpd_base64_decode_failed");
return 0;
}
- if (!(ret = auth(user, pass)))
- log_info1("Authentication failed");
+ if ((ret = auth(user, pass)))
+ log_info2("Access granted for user=\"%s\"", user);
+ else
+ log_info2("Authentication failed for user=\"%s\"", user);
free(user);
free(pass);
@@ -563,19 +584,20 @@ static void *
httpd_session_main (void *data)
#endif
{
- conndata_t *conn = (conndata_t *) data;
const char *msg = "SESSION 1.0\n";
int len = strlen (msg);
int done = 0;
char buffer[256]; /* temp buffer for recv() */
char header[4064]; /* received header */
hrequest_t *req = NULL; /* only for test */
+ conndata_t *conn;
httpd_conn_t *rconn = NULL;
hservice_t *service = NULL;
herror_t status;
header[0] = '\0';
len = 0;
+ conn = (conndata_t *) data;
log_verbose1 ("starting httpd_session_main()");
#ifdef HAVE_SSL
@@ -598,15 +620,19 @@ httpd_session_main (void *data)
/* call the service */
/* req = hrequest_new_from_buffer (header);*/
+ rconn = httpd_new (conn->sock);
+
while (!done)
{
log_verbose1 ("starting HTTP request");
- rconn = httpd_new (conn->sock);
+ /* XXX: only used in WSAreaper */
+ conn->atime = time(NULL);
if ((status = hrequest_new_from_socket (conn->sock, &req)) != H_OK)
{
/* "Request parse error!" */
+ /* XXX: may be "socket read error" */
if (herror_code (status) != HSOCKET_ERROR_SSLCLOSE)
{
httpd_send_internal_error (rconn, herror_message (status));
@@ -617,7 +643,7 @@ httpd_session_main (void *data)
else
{
char *conn_str = hpairnode_get_ignore_case (req->header, HEADER_CONNECTION);
- if (conn_str && strncasecmp (conn_str, "close", 5) == 0)
+ if (conn_str && strncasecmp (conn_str, "close", 6) == 0)
{
done = 1;
}
@@ -627,12 +653,11 @@ httpd_session_main (void *data)
}
httpd_request_print (req);
- service = httpd_find_service (req->path);
- if (service != NULL)
+ if ((service = httpd_find_service (req->path)))
{
log_verbose3 ("service '%s' for '%s' found", service->ctx, req->path);
- if (httpd_authenticate_request(req, service->auth)) {
+ if (_httpd_authenticate_request(req, service->auth)) {
if (service->func != NULL)
{
@@ -649,33 +674,39 @@ httpd_session_main (void *data)
httpd_send_internal_error (rconn, buffer);
}
}
- else {
+ else {
httpd_set_header(rconn, HEADER_WWW_AUTHENTICATE, "Basic realm=\"nanoHTTP\"");
httpd_send_header(rconn, 401, "Unauthorized");
- hsocket_send(conn->sock, "<html><head><title>Unauthorized</title></header><body><h1>Unauthorized</h1></body></html>");
- }
+ hsocket_send(conn->sock, "<html><head><title>Unauthorized</title></header><body><h1>Unauthorized request logged</h1></body></html>");
+ }
}
else
{
- sprintf (buffer, "service '%s' not found", req->path);
+ sprintf (buffer, "no service for '%s' found", req->path);
log_verbose1 (buffer);
httpd_send_internal_error (rconn, buffer);
}
+ hrequest_free(req);
}
}
- hsocket_close (conn->sock);
- log_verbose1 ("Marking connection as available");
- conn->sock.sock = 0;
- hrequest_free (req);
- httpd_free (rconn);
+ httpd_free(rconn);
+
+ hsocket_close (&(conn->sock));
#ifdef WIN32
CloseHandle ((HANDLE) conn->tid);
+#else
+ pthread_attr_destroy(&(conn->attr));
+#endif
+
+ hsocket_init(&(conn->sock));
+
+#ifdef WIN32
_endthread ();
return 0;
-#else
+#else
/* pthread_exits automagically */
return NULL;
#endif
@@ -809,7 +840,7 @@ static conndata_t *
_httpd_wait_for_empty_conn (void)
{
int i;
- for (i = 0;; i++)
+ for (i = 0; ; i++)
{
if (!_httpd_run)
return NULL;
@@ -817,9 +848,9 @@ _httpd_wait_for_empty_conn (void)
if (i >= _httpd_max_connections)
{
system_sleep (1);
- i = 0;
+ i = -1;
}
- else if (_httpd_connection[i].sock.sock == 0)
+ else if (_httpd_connection[i].sock.sock == HSOCKET_FREE)
{
break;
}
@@ -947,11 +978,11 @@ httpd_run (void)
&& herror_code (err) == SSL_ERROR_INIT*/
)
{
- hsocket_close (conn->sock);
+ hsocket_close(&(conn->sock));
hsocket_init(&(conn->sock));
- log_error1 (herror_message (err));
+ log_error1(herror_message (err));
continue;
}
else if (err != H_OK)
@@ -1061,14 +1092,17 @@ httpd_get_postdata (httpd_conn_t * conn, hrequest_t * req, long *received,
if (content_length == 0)
{
*received = 0;
- postdata = (char *) malloc (1);
+ if (!(postdata = (char *) malloc (1))) {
+
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
postdata[0] = '\0';
return postdata;
}
- postdata = (unsigned char *) malloc (content_length + 1);
- if (postdata == NULL)
+ if (!(postdata = (unsigned char *) malloc (content_length + 1)))
{
- log_error1 ("Not enough memory");
+ log_error2 ("malloc failed (%)", strerror(errno));
return NULL;
}
if (http_input_stream_read (req->in, postdata, (int) content_length) > 0)
@@ -1082,8 +1116,6 @@ httpd_get_postdata (httpd_conn_t * conn, hrequest_t * req, long *received,
}
-
-
/*
MIME support httpd_mime_* function set
*/
diff --git a/nanohttp/nanohttp-server.h b/nanohttp/nanohttp-server.h
index bf7405d..1768edd 100644
--- a/nanohttp/nanohttp-server.h
+++ b/nanohttp/nanohttp-server.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-server.h,v 1.14 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-server.h,v 1.15 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -25,10 +25,6 @@
#define NANO_HTTP_SERVER_H
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include <nanohttp/nanohttp-common.h>
#include <nanohttp/nanohttp-socket.h>
#include <nanohttp/nanohttp-request.h>
@@ -63,6 +59,10 @@ typedef struct tag_hservice
} hservice_t;
+#ifdef __cplusplus
+extern "C" {
+#endif
+
/*
Begin httpd_* function set
diff --git a/nanohttp/nanohttp-socket.c b/nanohttp/nanohttp-socket.c
index c3b2f85..77d4d9c 100644
--- a/nanohttp/nanohttp-socket.c
+++ b/nanohttp/nanohttp-socket.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-socket.c,v 1.52 2006/02/21 21:26:58 mrcsys Exp $
+* $Id: nanohttp-socket.c,v 1.53 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -136,12 +136,8 @@ hsocket_init(hsocket_t * sock)
{
log_verbose1("Starting hsocket init");
-#ifdef WIN32
memset(sock, 0, sizeof(hsocket_t));
-#else
- bzero(sock, sizeof(hsocket_t));
-#endif
- sock->sock = -1;
+ sock->sock = HSOCKET_FREE;
return H_OK;
}
@@ -342,49 +338,50 @@ hsocket_listen(hsocket_t sock)
return H_OK;
}
-/*--------------------------------------------------
-FUNCTION: hsocket_close
-----------------------------------------------------*/
-void
-hsocket_close(hsocket_t sock)
+#ifdef WIN32
+static inline void
+_hsocket_sys_close(hsocket_t *sock)
{
char junk[10];
-/* _hsocket_wait_until_receive(sock);*/
- log_verbose2("closing socket %d...", sock.sock);
-/*
- struct linger _linger;
- hsocket_block(sock,1);
- _linger.l_onoff =1;
- _linger.l_linger = 30000;
- setsockopt(sock, SOL_SOCKET, SO_LINGER, (const char*)&_linger, sizeof(struct linger));
-*/
-
-#ifdef WIN32
/* shutdown(sock,SD_RECEIVE); */
- shutdown(sock.sock, SD_SEND);
- while (recv(sock.sock, junk, sizeof(junk), 0) > 0) ;
+ shutdown(sock->sock, SD_SEND);
+ while (recv(sock->sock, junk, sizeof(junk), 0) > 0) ;
/* nothing */
- closesocket(sock.sock);
+ closesocket(sock->sock);
+ return;
+}
#else
- /* XXX m. campbell - It seems like the while loop here needs this */
- fcntl(sock.sock, F_SETFL, O_NONBLOCK);
+static inline void
+_hsocket_sys_close(hsocket_t *sock)
+{
+
+ shutdown(sock->sock, SHUT_RDWR);
+
+ return;
+}
+#endif
+
+/*--------------------------------------------------
+FUNCTION: hsocket_close
+----------------------------------------------------*/
+void
+hsocket_close(hsocket_t *sock)
+{
+ log_verbose3("closing socket %p (%d)...", sock, sock->sock);
+
#ifdef HAVE_SSL
- if (sock.ssl)
+ if (sock->ssl)
{
log_verbose1("Closing SSL");
- ssl_cleanup(sock.ssl);
- sock.ssl = NULL;
+ ssl_cleanup(sock->ssl);
+ sock->ssl = NULL;
}
#endif
- shutdown(sock.sock, SHUT_RDWR);
- while (recv(sock.sock, junk, sizeof(junk), 0) > 0) ;
- /* nothing */
- close(sock.sock);
-#endif
+ _hsocket_sys_close(sock);
log_verbose1("socket closed");
@@ -427,11 +424,17 @@ hsocket_nsend(hsocket_t sock, const byte_t * bytes, int n)
/* size = _test_send_to_file(filename, bytes, n); */
#ifdef WIN32
if (size == INVALID_SOCKET)
+ {
if (WSAGetLastError() == WSAEWOULDBLOCK)
+ {
continue;
+ }
else
+ {
return herror_new("hsocket_nsend", HSOCKET_ERROR_SEND,
"Socket error: %d", errno);
+ }
+ }
#else
if (size == -1)
{
diff --git a/nanohttp/nanohttp-socket.h b/nanohttp/nanohttp-socket.h
index f5f8aa7..63d55dd 100644
--- a/nanohttp/nanohttp-socket.h
+++ b/nanohttp/nanohttp-socket.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-socket.h,v 1.23 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-socket.h,v 1.24 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003 Ferhat Ayaz
@@ -24,14 +24,10 @@
#ifndef NANO_HTTP_SOCKET_H
#define NANO_HTTP_SOCKET_H
-#ifdef __cplusplus
-extern "C" {
-#endif
+#include <time.h>
#include <nanohttp/nanohttp-common.h>
-#include <time.h>
-
#ifdef HAVE_SSL
#include <openssl/ssl.h>
#endif
@@ -40,6 +36,7 @@ extern "C" {
#include <winsock2.h>
#endif
+#define HSOCKET_FREE -1
/*
Socket definition
@@ -55,7 +52,7 @@ typedef struct hsocket_t
#ifdef WIN32
SOCKET sock;
#else
- int sock;
+ volatile int sock;
#endif
int block;
@@ -65,7 +62,9 @@ typedef struct hsocket_t
typedef int socklen_t;
#endif
-
+#ifdef __cplusplus
+extern "C" {
+#endif
/**
@@ -145,7 +144,7 @@ herror_t hsocket_open(hsocket_t * sock, const char *host, int port);
@param sock the socket to close
*/
-void hsocket_close(hsocket_t sock);
+void hsocket_close(hsocket_t *sock);
/**
diff --git a/nanohttp/nanohttp-ssl.h b/nanohttp/nanohttp-ssl.h
index 798a1ee..1cdafb2 100644
--- a/nanohttp/nanohttp-ssl.h
+++ b/nanohttp/nanohttp-ssl.h
@@ -25,10 +25,6 @@
/* Do enter only if --with-ssl was specified by the configure script */
#ifdef HAVE_SSL
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#ifdef TRU64
#include <arpa/inet.h>
typedef unsigned int uint32_t;
@@ -61,6 +57,10 @@ typedef struct Con
* Callback for password checker
*/
+#ifdef __cplusplus
+extern "C" {
+#endif
+
//static int pw_cb(char* buf, int num, int rwflag, void *userdata);
/*
diff --git a/nanohttp/nanohttp-stream.c b/nanohttp/nanohttp-stream.c
index 8908e54..0d8188a 100755
--- a/nanohttp/nanohttp-stream.c
+++ b/nanohttp/nanohttp-stream.c
@@ -1,5 +1,5 @@
/******************************************************************
-* $Id: nanohttp-stream.c,v 1.10 2006/02/18 20:14:36 snowdrop Exp $
+* $Id: nanohttp-stream.c,v 1.11 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -25,10 +25,18 @@
#include <config.h>
#endif
+#ifdef HAVE_STDIO_H
+#include <stdio.h>
+#endif
+
#ifdef HAVE_STRING_H
#include <string.h>
#endif
+#ifdef HAVE_ERRNO_H
+#include <errno.h>
+#endif
+
#ifdef MEM_DEBUG
#include <utils/alloc.h>
#endif
@@ -88,7 +96,12 @@ http_input_stream_new(hsocket_t sock, hpair_t * header)
/* Paranoya check */
/* if (header == NULL) return NULL; */
/* Create object */
- result = (http_input_stream_t *) malloc(sizeof(http_input_stream_t));
+ if (!(result = (http_input_stream_t *) malloc(sizeof(http_input_stream_t))))
+ {
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
+
result->sock = sock;
result->err = H_OK;
@@ -131,17 +144,27 @@ http_input_stream_t *
http_input_stream_new_from_file(const char *filename)
{
http_input_stream_t *result;
- FILE *fd = fopen(filename, "rb");
+ FILE *fd;
+
+ if (!(fd = fopen(filename, "rb"))) {
- if (fd == NULL)
+ log_error2("fopen failed (%s)", strerror(errno));
return NULL;
+ }
/* Create object */
- result = (http_input_stream_t *) malloc(sizeof(http_input_stream_t));
+ if (!(result = (http_input_stream_t *) malloc(sizeof(http_input_stream_t))))
+ {
+ log_error2("malloc failed (%s)", strerror(errno));
+ fclose(fd);
+ return NULL;
+ }
+
result->type = HTTP_TRANSFER_FILE;
result->fd = fd;
result->deleteOnExit = 0;
strcpy(result->filename, filename);
+
return result;
}
@@ -225,7 +248,7 @@ _http_input_stream_chunked_read_chunk_size(http_input_stream_t * stream)
{
stream->err = herror_new("_http_input_stream_chunked_read_chunk_size",
GENERAL_INVALID_PARAM,
- "This should never happens!");
+ "This should never happen!");
return -1;
}
@@ -262,7 +285,7 @@ _http_input_stream_chunked_read_chunk_size(http_input_stream_t * stream)
i++;
}
- /* this should never happens */
+ /* this should never happen */
stream->err =
herror_new("_http_input_stream_chunked_read_chunk_size",
STREAM_ERROR_NO_CHUNK_SIZE, "reached max line == %d", i);
@@ -343,7 +366,7 @@ _http_input_stream_chunked_read(http_input_stream_t * stream, byte_t * dest,
{
stream->err = herror_new("_http_input_stream_chunked_read",
GENERAL_INVALID_PARAM,
- "This should never happens(remain=%d)(status=%d)!",
+ "This should never happen (remain=%d)(status=%d)!",
remain, status);
return -1;
}
@@ -356,7 +379,7 @@ _http_input_stream_chunked_read(http_input_stream_t * stream, byte_t * dest,
{
stream->err = herror_new("_http_input_stream_chunked_read",
GENERAL_INVALID_PARAM,
- "This should never happens(size=%d)(status=%d)!",
+ "This should never happen (size=%d)(status=%d)!",
size, status);
return -1;
}
@@ -403,17 +426,16 @@ static int
_http_input_stream_file_read(http_input_stream_t * stream, byte_t * dest,
int size)
{
- int readed;
+ size_t len;
- readed = fread(dest, 1, size, stream->fd);
- if (readed == -1)
+ if ((len = fread(dest, 1, size, stream->fd)) == -1)
{
stream->err = herror_new("_http_input_stream_file_read",
HSOCKET_ERROR_RECEIVE, "fread() returned -1");
return -1;
}
- return readed;
+ return len;
}
/**
@@ -452,8 +474,8 @@ http_input_stream_is_ready(http_input_stream_t * stream)
int
http_input_stream_read(http_input_stream_t * stream, byte_t * dest, int size)
{
- int readed = 0;
- /* paranoya check */
+ int len = 0;
+ /* paranoia check */
if (stream == NULL)
{
return -1;
@@ -465,16 +487,16 @@ http_input_stream_read(http_input_stream_t * stream, byte_t * dest, int size)
switch (stream->type)
{
case HTTP_TRANSFER_CONTENT_LENGTH:
- readed = _http_input_stream_content_length_read(stream, dest, size);
+ len = _http_input_stream_content_length_read(stream, dest, size);
break;
case HTTP_TRANSFER_CHUNKED:
- readed = _http_input_stream_chunked_read(stream, dest, size);
+ len = _http_input_stream_chunked_read(stream, dest, size);
break;
case HTTP_TRANSFER_CONNECTION_CLOSE:
- readed = _http_input_stream_connection_closed_read(stream, dest, size);
+ len = _http_input_stream_connection_closed_read(stream, dest, size);
break;
case HTTP_TRANSFER_FILE:
- readed = _http_input_stream_file_read(stream, dest, size);
+ len = _http_input_stream_file_read(stream, dest, size);
break;
default:
stream->err = herror_new("http_input_stream_read",
@@ -483,7 +505,7 @@ http_input_stream_read(http_input_stream_t * stream, byte_t * dest, int size)
return -1;
}
- return readed;
+ return len;
}
@@ -511,7 +533,12 @@ http_output_stream_new(hsocket_t sock, hpair_t * header)
return NULL;
*/
/* Create object */
- result = (http_output_stream_t *) malloc(sizeof(http_output_stream_t));
+ if (!(result = (http_output_stream_t *) malloc(sizeof(http_output_stream_t))))
+ {
+ log_error2("malloc failed (%s)", strerror(errno));
+ return NULL;
+ }
+
result->sock = sock;
result->sent = 0;
@@ -548,6 +575,8 @@ void
http_output_stream_free(http_output_stream_t * stream)
{
free(stream);
+
+ return;
}
/**
@@ -564,23 +593,20 @@ http_output_stream_write(http_output_stream_t * stream,
if (stream->type == HTTP_TRANSFER_CHUNKED)
{
sprintf(chunked, "%x\r\n", size);
- status = hsocket_send(stream->sock, chunked);
- if (status != H_OK)
+ if ((status = hsocket_send(stream->sock, chunked)) != H_OK)
return status;
}
if (size > 0)
{
_log_str("stream.out", (char *) bytes, size);
- status = hsocket_nsend(stream->sock, bytes, size);
- if (status != H_OK)
+ if ((status = hsocket_nsend(stream->sock, bytes, size)) != H_OK)
return status;
}
if (stream->type == HTTP_TRANSFER_CHUNKED)
{
- status = hsocket_send(stream->sock, "\r\n");
- if (status != H_OK)
+ if ((status = hsocket_send(stream->sock, "\r\n")) != H_OK)
return status;
}
@@ -606,8 +632,7 @@ http_output_stream_flush(http_output_stream_t * stream)
if (stream->type == HTTP_TRANSFER_CHUNKED)
{
- status = hsocket_send(stream->sock, "0\r\n\r\n");
- if (status != H_OK)
+ if ((status = hsocket_send(stream->sock, "0\r\n\r\n")) != H_OK)
return status;
}
diff --git a/nanohttp/nanohttp-stream.h b/nanohttp/nanohttp-stream.h
index 0cc3ab7..ac78603 100755
--- a/nanohttp/nanohttp-stream.h
+++ b/nanohttp/nanohttp-stream.h
@@ -1,5 +1,5 @@
/******************************************************************
- * $Id: nanohttp-stream.h,v 1.8 2006/02/27 00:26:23 snowdrop Exp $
+ * $Id: nanohttp-stream.h,v 1.9 2006/02/27 22:26:02 snowdrop Exp $
*
* CSOAP Project: A http client/server library in C
* Copyright (C) 2003-2004 Ferhat Ayaz
@@ -24,12 +24,15 @@
#ifndef NANO_HTTP_STREAM_H
#define NANO_HTTP_STREAM_H
+#include <stdio.h>
+
+#include <nanohttp/nanohttp-socket.h>
+#include <nanohttp/nanohttp-common.h>
+
#ifdef __cplusplus
extern "C" {
#endif
-#include <stdio.h>
-
void _log_str(char *fn, char *str, int size);
/*
@@ -57,12 +60,6 @@ void _log_str(char *fn, char *str, int size);
*/
-#include <nanohttp/nanohttp-socket.h>
-#include <nanohttp/nanohttp-common.h>
-
-#include <stdio.h>
-
-
/**
Transfer types supported while
sending/receiving data.