Commit 646d1e1c50ad972e8098c2b23e531d58a043c181

Authored by Georg Hopp
1 parent 784364db

Added a new abstraction: hash. A a lot of things within http are key/value thing…

…s based on stings i created this generic hash class and use it to store the header right now. In future it will also be used to store cookie, get and post vars
  1 +#ifndef __HASH_H__
  2 +#define __HASH_H__
  3 +
  4 +#include <sys/types.h>
  5 +
  6 +#include "class.h"
  7 +
  8 +
  9 +CLASS(Hash) {
  10 + void * root;
  11 +};
  12 +
  13 +void * hashAdd(Hash, void *);
  14 +void * hashDelete(Hash, const char *, size_t);
  15 +void * hashGet(Hash, const char *, size_t);
  16 +void hashEach(Hash, void (*)(const void*));
  17 +
  18 +#endif // __HASH_H__
  19 +
  20 +// vim: set ts=4 sw=4:
... ...
... ... @@ -41,8 +41,6 @@ CLASS(HttpHeader) {
41 41 size_t size; //!< full size of this header
42 42 };
43 43
44   -HttpHeader httpHeaderAdd(const HttpHeader *, HttpHeader);
45   -HttpHeader httpHeaderGet(const HttpHeader *, const char *, size_t);
46 44 size_t httpHeaderToString(HttpHeader, char *);
47 45
48 46 #endif // __HTTP_HEADER_H__
... ...
... ... @@ -25,7 +25,7 @@
25 25 #define __HTTP_MESSAGE__
26 26
27 27 #include "class.h"
28   -#include "http/header.h"
  28 +#include "hash.h"
29 29 #include "stream.h"
30 30
31 31 typedef enum e_HttpMessageType {
... ... @@ -37,7 +37,7 @@ typedef enum e_HttpMessageType {
37 37 CLASS(HttpMessage) {
38 38 char * version;
39 39
40   - HttpHeader header;
  40 + Hash header;
41 41
42 42 HttpMessageType type;
43 43 Stream handle;
... ...
  1 +/**
  2 + * \file
  3 + * The logger interface.
  4 + *
  5 + * \author Georg Hopp
  6 + *
  7 + * \copyright
  8 + * Copyright (C) 2012 Georg Hopp
  9 + *
  10 + * This program is free software: you can redistribute it and/or modify
  11 + * it under the terms of the GNU General Public License as published by
  12 + * the Free Software Foundation, either version 3 of the License, or
  13 + * (at your option) any later version.
  14 + *
  15 + * This program is distributed in the hope that it will be useful,
  16 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
  17 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  18 + * GNU General Public License for more details.
  19 + *
  20 + * You should have received a copy of the GNU General Public License
  21 + * along with this program. If not, see <http://www.gnu.org/licenses/>.
  22 + */
  23 +
  24 +#ifndef __INTERFACE_HASHABLE_H__
  25 +#define __INTERFACE_HASHABLE_H__
  26 +
  27 +#include "interface.h"
  28 +
  29 +typedef unsigned long (* fptr_hashableGetHash)(void *);
  30 +typedef void (* fptr_hashableHandleDouble)(void *, void *);
  31 +
  32 +extern const struct interface i_Hashable;
  33 +
  34 +struct i_Hashable {
  35 + const struct interface * const _;
  36 + fptr_hashableGetHash getHash;
  37 + fptr_hashableHandleDouble handleDouble;
  38 +};
  39 +
  40 +extern unsigned long hashableGetHash(void *);
  41 +extern void hashableHandleDouble(void *, void *);
  42 +
  43 +#endif // __INTERFACE_HASHABLE_H__
  44 +
  45 +// vim: set ts=4 sw=4:
... ...
... ... @@ -6,6 +6,12 @@ IFACE = interface/class.c interface/stream_reader.c interface/logger.c \
6 6 interface/subject.c interface/observer.c interface.c
7 7 SOCKET = socket.c socket/accept.c socket/connect.c socket/listen.c
8 8 STREAM = stream.c stream/read.c stream/write.c
  9 +HASH = hash.c \
  10 + hash/add.c \
  11 + hash/get.c \
  12 + hash/delete.c \
  13 + hash/each.c \
  14 + interface/hashable.c
9 15 SERVER = server.c server/run.c server/close_conn.c server/poll.c \
10 16 server/handle_accept.c server/read.c server/write.c
11 17 LOGGER = logger.c logger/stderr.c logger/syslog.c
... ... @@ -44,7 +50,7 @@ WORKER = http/worker.c \
44 50 http/worker/write.c \
45 51 http/worker/get_asset.c \
46 52 http/worker/add_common_header.c
47   -HEADER = http/header.c http/header/get.c http/header/add.c \
  53 +HEADER = http/header.c \
48 54 http/header/to_string.c
49 55 SESSION = session.c session/add.c session/get.c session/delete.c
50 56 UTILS = utils/hash.c \
... ... @@ -61,6 +67,6 @@ bin_PROGRAMS = webgameserver
61 67 webgameserver_SOURCES = webgameserver.c \
62 68 $(IFACE) $(SOCKET) $(SERVER) $(LOGGER) $(MSG) $(REQ) \
63 69 $(WRITER) $(RESP) $(HEADER) $(PARSER) $(WORKER) $(CB) \
64   - $(UTILS) $(MSGQ) $(SESSION) $(STREAM)
  70 + $(UTILS) $(MSGQ) $(SESSION) $(STREAM) $(HASH)
65 71 webgameserver_CFLAGS = -Wall -I ../include/
66 72 webgameserver_LDFLAGS = -lrt -lssl
... ...
  1 +#define _GNU_SOURCE
  2 +
  3 +#include <search.h>
  4 +#include <stdarg.h>
  5 +
  6 +#include "hash.h"
  7 +#include "class.h"
  8 +#include "interface/class.h"
  9 +
  10 +static
  11 +int
  12 +hashCtor(void * _this, va_list * params)
  13 +{
  14 + return 0;
  15 +}
  16 +
  17 +static
  18 +inline
  19 +void
  20 +tDelete(void * node)
  21 +{
  22 + delete(node);
  23 +}
  24 +
  25 +static
  26 +void
  27 +hashDtor(void * _this)
  28 +{
  29 + Hash this = _this;
  30 +
  31 + /**
  32 + * this is a GNU extension...anyway on most non
  33 + * GNUish systems i would not use tsearch anyway
  34 + * as the trees will be unbalanced.
  35 + */
  36 + tdestroy(this->root, tDelete);
  37 +}
  38 +
  39 +INIT_IFACE(Class, hashCtor, hashDtor, NULL);
  40 +CREATE_CLASS(Hash, NULL, IFACE(Class));
  41 +
  42 +// vim: set ts=4 sw=4:
... ...
  1 +#include <search.h>
  2 +
  3 +#include "hash.h"
  4 +#include "interface/hashable.h"
  5 +#include "interface/class.h"
  6 +
  7 +static
  8 +inline
  9 +int
  10 +hashAddComp(const void * a, const void * b)
  11 +{
  12 + return hashableGetHash((void*)b) - hashableGetHash((void*)a);
  13 +}
  14 +
  15 +void *
  16 +hashAdd(Hash this, void * operand)
  17 +{
  18 + void * found = tsearch(operand, &(this->root), hashAddComp);
  19 +
  20 + if (NULL == found) {
  21 + return NULL;
  22 + }
  23 +
  24 + if (operand != *(void**)found) {
  25 + hashableHandleDouble(*(void**)found, operand);
  26 + delete(operand);
  27 + }
  28 +
  29 + return *(void**)found;
  30 +}
  31 +
  32 +// vim: set ts=4 sw=4:
... ...
  1 +#include <search.h>
  2 +#include <sys/types.h>
  3 +
  4 +#include "hash.h"
  5 +#include "interface/hashable.h"
  6 +#include "utils/hash.h"
  7 +
  8 +static
  9 +inline
  10 +int
  11 +hashDeleteComp(const void * a, const void * b)
  12 +{
  13 + return hashableGetHash((void*)b) - *(const unsigned long*)a;
  14 +}
  15 +
  16 +void *
  17 +hashDelete(Hash this, const char * search, size_t nsearch)
  18 +{
  19 + unsigned long hash = sdbm((const unsigned char *)search, nsearch);
  20 + void * found = tfind(&hash, &(this->root), hashDeleteComp);
  21 +
  22 + return (NULL != found)? *(void**)found : NULL;
  23 +}
  24 +
  25 +// vim: set ts=4 sw=4:
... ...
  1 +#include <search.h>
  2 +
  3 +#include "hash.h"
  4 +
  5 +static void (*cb)(void*);
  6 +
  7 +static
  8 +inline
  9 +void
  10 +walk(const void * node, const VISIT which, const int depth)
  11 +{
  12 + if (endorder == which || leaf == which) {
  13 + cb(*(void**)node);
  14 + }
  15 +}
  16 +
  17 +void
  18 +hashEach(Hash this, void (*callback)(const void*))
  19 +{
  20 + cb = callback;
  21 +
  22 + twalk(this->root, walk);
  23 +}
  24 +
  25 +// vim: set ts=4 sw=4:
... ...
  1 +#include <search.h>
  2 +#include <sys/types.h>
  3 +
  4 +#include "hash.h"
  5 +#include "interface/hashable.h"
  6 +#include "utils/hash.h"
  7 +
  8 +static
  9 +inline
  10 +int
  11 +hashGetComp(const void * a, const void * b)
  12 +{
  13 + return hashableGetHash((void*)b) - *(const unsigned long*)a;
  14 +}
  15 +
  16 +void *
  17 +hashGet(Hash this, const char * search, size_t nsearch)
  18 +{
  19 + unsigned long hash = sdbm((const unsigned char *)search, nsearch);
  20 + void * found = tfind(&hash, &(this->root), hashGetComp);
  21 +
  22 + return (NULL != found)? *(void**)found : NULL;
  23 +}
  24 +
  25 +// vim: set ts=4 sw=4:
... ...
... ... @@ -27,6 +27,7 @@
27 27 #include "class.h"
28 28 #include "interface/class.h"
29 29 #include "http/header.h"
  30 +#include "interface/hashable.h"
30 31
31 32 #include "utils/hash.h"
32 33 #include "utils/memory.h"
... ... @@ -72,7 +73,35 @@ httpHeaderDtor(void * _this)
72 73 }
73 74 }
74 75
  76 +static
  77 +unsigned long
  78 +httpHeaderGetHash(void * _this)
  79 +{
  80 + HttpHeader this = _this;
  81 +
  82 + return this->hash;
  83 +}
  84 +
  85 +static
  86 +void
  87 +httpHeaderHandleDouble(void * _this, void * _double)
  88 +{
  89 + HttpHeader this = _this;
  90 + HttpHeader doub = _double;
  91 +
  92 + if (this->cvalue >= N_VALUES) {
  93 + //! \todo do dome error logging...or change to HEAP
  94 + return;
  95 + }
  96 +
  97 + (this->nvalue)[this->cvalue] = (doub->nvalue)[0];
  98 + (this->value)[(this->cvalue)++] = (doub->value)[0];
  99 + this->size += doub->size;
  100 + (doub->value)[0] = NULL;
  101 +}
  102 +
75 103 INIT_IFACE(Class, httpHeaderCtor, httpHeaderDtor, NULL);
76   -CREATE_CLASS(HttpHeader, NULL, IFACE(Class));
  104 +INIT_IFACE(Hashable, httpHeaderGetHash, httpHeaderHandleDouble);
  105 +CREATE_CLASS(HttpHeader, NULL, IFACE(Class), IFACE(Hashable));
77 106
78 107 // vim: set ts=4 sw=4:
... ...
1   -/**
2   - * \file
3   - *
4   - * \author Georg Hopp
5   - *
6   - * \copyright
7   - * Copyright (C) 2012 Georg Hopp
8   - *
9   - * This program is free software: you can redistribute it and/or modify
10   - * it under the terms of the GNU General Public License as published by
11   - * the Free Software Foundation, either version 3 of the License, or
12   - * (at your option) any later version.
13   - *
14   - * This program is distributed in the hope that it will be useful,
15   - * but WITHOUT ANY WARRANTY; without even the implied warranty of
16   - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17   - * GNU General Public License for more details.
18   - *
19   - * You should have received a copy of the GNU General Public License
20   - * along with this program. If not, see <http://www.gnu.org/licenses/>.
21   - */
22   -
23   -#include <search.h>
24   -#include <stdio.h>
25   -#include <stdlib.h>
26   -#include <string.h>
27   -
28   -#include "class.h"
29   -#include "interface/class.h"
30   -#include "http/header.h"
31   -#include "utils/hash.h"
32   -
33   -static
34   -inline
35   -int
36   -comp(const void * _a, const void * _b)
37   -{
38   - HttpHeader a = (HttpHeader)_a;
39   - HttpHeader b = (HttpHeader)_b;
40   - return (a->hash < b->hash)? -1 : (a->hash > b->hash)? 1 : 0;
41   -}
42   -
43   -HttpHeader
44   -httpHeaderAdd(const HttpHeader * root, HttpHeader header)
45   -{
46   - HttpHeader * _found = tsearch(header, (void **)root, comp);
47   - HttpHeader found;
48   -
49   - if (NULL == _found) {
50   - return NULL;
51   - }
52   -
53   - found = *_found;
54   -
55   - if (found != header) {
56   - if (found->cvalue >= N_VALUES) {
57   - return NULL;
58   - }
59   - (found->nvalue)[found->cvalue] = (header->nvalue)[0];
60   - (found->value)[(found->cvalue)++] = (header->value)[0];
61   - found->size += header->size;
62   - (header->value)[0] = NULL;
63   - delete(header);
64   - }
65   -
66   - return found;
67   -}
68   -
69   -// vim: set ts=4 sw=4:
... ... @@ -32,20 +32,12 @@
32 32
33 33 #include "class.h"
34 34 #include "interface/class.h"
35   -
  35 +#include "hash.h"
36 36 #include "http/message.h"
37 37 #include "utils/memory.h"
38 38
39 39
40 40 static
41   -inline
42   -void
43   -tDelete(void * node)
44   -{
45   - delete(node);
46   -}
47   -
48   -static
49 41 int
50 42 httpMessageCtor(void * _this, va_list * params)
51 43 {
... ... @@ -55,6 +47,8 @@ httpMessageCtor(void * _this, va_list * params)
55 47 this->version = calloc(1, strlen(version)+1);
56 48 strcpy(this->version, version);
57 49
  50 + this->header = new(Hash);
  51 +
58 52 return 0;
59 53 }
60 54
... ... @@ -64,15 +58,9 @@ httpMessageDtor(void * _this)
64 58 {
65 59 HttpMessage this = _this;
66 60
  61 + delete(this->header);
67 62 FREE(this->version);
68 63
69   - /**
70   - * this is a GNU extension...anyway on most non
71   - * GNUish systems i would not use tsearch anyway
72   - * as the trees will be unbalanced.
73   - */
74   - tdestroy(this->header, tDelete);
75   -
76 64 switch (this->type) {
77 65 case HTTP_MESSAGE_BUFFERED:
78 66 FREE(this->body);
... ...
... ... @@ -31,6 +31,7 @@
31 31 #include "utils/memory.h"
32 32
33 33 #include "commons.h"
  34 +#include "hash.h"
34 35
35 36 char
36 37 httpMessageHasKeepAlive(HttpMessage message)
... ... @@ -39,7 +40,7 @@ httpMessageHasKeepAlive(HttpMessage message)
39 40 size_t size;
40 41 char * value;
41 42
42   - header = httpHeaderGet(&(message->header), CSTRA("connection"));
  43 + header = hashGet(message->header, CSTRA("connection"));
43 44
44 45 if (NULL == header) {
45 46 return 0;
... ...
... ... @@ -28,17 +28,16 @@
28 28 #include "http/response.h"
29 29 #include "http/header.h"
30 30 #include "interface/http_intro.h"
  31 +#include "hash.h"
31 32
32 33 static size_t size;
33 34
34 35 static
35 36 inline
36 37 void
37   -addHeaderSize(const void * node, const VISIT which, const int depth)
  38 +addHeaderSize(const void * node)
38 39 {
39   - if (endorder == which || leaf == which) {
40   - size += (*(HttpHeader *)node)->size;
41   - }
  40 + size += ((HttpHeader)node)->size;
42 41 }
43 42
44 43 size_t
... ... @@ -46,7 +45,7 @@ httpMessageHeaderSizeGet(HttpMessage message)
46 45 {
47 46 size = httpIntroSizeGet(message);
48 47
49   - twalk(message->header, addHeaderSize);
  48 + hashEach(message->header, addHeaderSize);
50 49 size += 2;
51 50
52 51 return size;
... ...
... ... @@ -27,15 +27,16 @@
27 27 #include "http/response.h"
28 28 #include "http/header.h"
29 29 #include "interface/http_intro.h"
  30 +#include "hash.h"
30 31
31 32 static char * string;
32 33
  34 +static
  35 +inline
33 36 void
34   -addHeaderString(const void * node, const VISIT which, const int depth)
  37 +addHeaderString(const void * node)
35 38 {
36   - if (endorder == which || leaf == which) {
37   - string += httpHeaderToString(*(HttpHeader *)node, string);
38   - }
  39 + string += httpHeaderToString((HttpHeader)node, string);
39 40 }
40 41
41 42 char *
... ... @@ -45,7 +46,7 @@ httpMessageHeaderToString(HttpMessage response, char * _string)
45 46
46 47 string = httpIntroToString(response, _string);
47 48
48   - twalk(message->header, addHeaderString);
  49 + hashEach(message->header, addHeaderString);
49 50
50 51 *string++ = '\r';
51 52 *string++ = '\n';
... ...
... ... @@ -29,6 +29,7 @@
29 29 #include "http/header.h"
30 30 #include "http/parser.h"
31 31 #include "http/message.h"
  32 +#include "hash.h"
32 33
33 34 #define MAX(x,y) ((x) > (y) ? (x) : (y))
34 35
... ... @@ -66,8 +67,7 @@ httpParserHeader(
66 67 current->dbody = 0;
67 68 }
68 69
69   - httpHeaderAdd(
70   - &(current->header),
  70 + hashAdd(current->header,
71 71 new(HttpHeader, name, nname, value, lend - value));
72 72 }
73 73
... ...
... ... @@ -30,6 +30,7 @@
30 30 #include "http/header.h"
31 31
32 32 #include "utils/memory.h"
  33 +#include "hash.h"
33 34
34 35 HttpResponse
35 36 httpResponse304(
... ... @@ -47,11 +48,11 @@ httpResponse304(
47 48 message->nbody = 0;
48 49 message->body = NULL;
49 50
50   - httpHeaderAdd(&(message->header),
  51 + hashAdd(message->header,
51 52 new(HttpHeader, CSTRA("Content-Type"), mime, nmime));
52   - httpHeaderAdd(&(message->header),
  53 + hashAdd(message->header,
53 54 new(HttpHeader, CSTRA("ETag"), etag, netag));
54   - httpHeaderAdd(&(message->header),
  55 + hashAdd(message->header,
55 56 new(HttpHeader, CSTRA("Last-Modified"), mtime, nmtime));
56 57
57 58 return response;
... ...
... ... @@ -33,6 +33,7 @@
33 33 #include "http/header.h"
34 34
35 35 #include "utils/memory.h"
  36 +#include "hash.h"
36 37
37 38 #define RESP_DATA "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n" \
38 39 "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\"\n" \
... ... @@ -52,7 +53,7 @@ httpResponse404()
52 53 response = new(HttpResponse, "HTTP/1.1", 404, "Not Found");
53 54 message = (HttpMessage)response;
54 55
55   - httpHeaderAdd(&(message->header),
  56 + hashAdd(message->header,
56 57 new(HttpHeader, CSTRA("Content-Type"), CSTRA("text/html")));
57 58
58 59 message->type = HTTP_MESSAGE_BUFFERED;
... ...
... ... @@ -35,7 +35,7 @@
35 35 #include "http/header.h"
36 36
37 37 #include "utils/memory.h"
38   -
  38 +#include "hash.h"
39 39
40 40 HttpResponse
41 41 httpResponseAsset(
... ... @@ -73,11 +73,11 @@ httpResponseAsset(
73 73 message->handle = new(Stream, STREAM_FD, handle);
74 74 message->nbody = st.st_size;
75 75
76   - httpHeaderAdd(&(message->header),
  76 + hashAdd(message->header,
77 77 new(HttpHeader, CSTRA("Content-Type"), mime, nmime));
78   - httpHeaderAdd(&(message->header),
  78 + hashAdd(message->header,
79 79 new(HttpHeader, CSTRA("ETag"), etag, netag));
80   - httpHeaderAdd(&(message->header),
  80 + hashAdd(message->header,
81 81 new(HttpHeader, CSTRA("Last-Modified"), mtime, nmtime));
82 82
83 83 return response;
... ...
... ... @@ -34,6 +34,7 @@
34 34 #include "http/header.h"
35 35
36 36 #include "utils/memory.h"
  37 +#include "hash.h"
37 38
38 39 #define RESP_DATA "<form action=\"/me/\" method=\"POST\">" \
39 40 "<input name=\"username\" type=\"text\" />" \
... ... @@ -49,7 +50,7 @@ httpResponseLoginForm()
49 50 response = new(HttpResponse, "HTTP/1.1", 200, "OK");
50 51 message = (HttpMessage)response;
51 52
52   - httpHeaderAdd(&(message->header),
  53 + hashAdd(message->header,
53 54 new(HttpHeader, CSTRA("Content-Type"), CSTRA("text/html")));
54 55
55 56 message->type = HTTP_MESSAGE_BUFFERED;
... ...
1   -/**
2   - * \file
3   - *
4   - * \author Georg Hopp
5   - *
6   - * \copyright
7   - * Copyright (C) 2012 Georg Hopp
8   - *
9   - * This program is free software: you can redistribute it and/or modify
10   - * it under the terms of the GNU General Public License as published by
11   - * the Free Software Foundation, either version 3 of the License, or
12   - * (at your option) any later version.
13   - *
14   - * This program is distributed in the hope that it will be useful,
15   - * but WITHOUT ANY WARRANTY; without even the implied warranty of
16   - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17   - * GNU General Public License for more details.
18   - *
19   - * You should have received a copy of the GNU General Public License
20   - * along with this program. If not, see <http://www.gnu.org/licenses/>.
21   - */
22   -
23   -#include <stdlib.h>
24   -#include <string.h>
25   -#include <stdio.h>
26   -#include <time.h>
27   -#include <sys/types.h>
28   -
29   -#include "class.h"
30   -#include "interface/class.h"
31   -
32   -#include "http/response.h"
33   -#include "http/message.h"
34   -#include "http/header.h"
35   -
36   -#include "utils/memory.h"
37   -
38   -
39   -#define RESP_DATA "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n" \
40   - "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\"\n" \
41   - " \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n" \
42   - "<html xmlns=\"http://www.w3.org/1999/xhtml\" xml:lang=\"en\" lang=\"en\">" \
43   - "<head>" \
44   - "<title>My own little Web-App</title>" \
45   - "<style type=\"text/css\">" \
46   - "div#randval {" \
47   - "left: 200px;" \
48   - "top: 100px;" \
49   - "position: fixed;" \
50   - "background-color: white;" \
51   - "border: 1px solid black;" \
52   - "}" \
53   - "div.hide#randval {" \
54   - "top: -500px;" \
55   - "}" \
56   - ".small {" \
57   - "font-size: small;" \
58   - "}" \
59   - "</style>" \
60   - "<script type=\"text/javascript\" src=\"/assets/js/jquery\"></script>" \
61   - "<script type=\"text/javascript\" src=\"/assets/js/serverval\"></script>" \
62   - "<script>" \
63   - "$(document).ready(function() {" \
64   - "var sval = new ServerVal(\"#randval\");" \
65   - "$(\"a\").click(function() {" \
66   - "sval.start();" \
67   - "});" \
68   - "});" \
69   - "</script>" \
70   - "</head>" \
71   - "<body>"
72   - "<ul id=\"menu\">" \
73   - "<li>serverval</li>" \
74   - "</ul>" \
75   - "<div id=\"randval\" class=\"hide\">" \
76   - "<span class=\"small\">" \
77   - "Value created at: <br /><span></span><br>" \
78   - "Next value in: <span></span><br />" \
79   - "</span>" \
80   - "Value: <span></span>" \
81   - "</div>" \
82   - "<div id=\"main\">" \
83   - "<h1>Testpage</h1>" \
84   - "Welcome %s<br />" \
85   - "<img src=\"/image/\" />" \
86   - "</div>" \
87   - "<hr /><div id=\"msg\"></div>" \
88   - "</body>" \
89   - "</html>"
90   -
91   -HttpResponse
92   -httpResponseMe(char * uname)
93   -{
94   - HttpResponse response;
95   - HttpMessage message;
96   -
97   - response = new(HttpResponse, "HTTP/1.1", 200, "OK");
98   - message = (HttpMessage)response;
99   -
100   - httpHeaderAdd(&(message->header),
101   - new(HttpHeader, CSTRA("Content-Type"), CSTRA("text/html")));
102   - httpHeaderAdd(&(message->header),
103   - new(HttpHeader, CSTRA("Set-Cookie"), CSTRA("name=Georg+Hopp")));
104   - httpHeaderAdd(&(message->header),
105   - new(HttpHeader, CSTRA("Set-Cookie"), CSTRA("profession=coder")));
106   -
107   - message->type = HTTP_MESSAGE_BUFFERED;
108   - message->nbody = sizeof(RESP_DATA)-1-2+strlen(uname); //!< the two are the %s
109   - message->body = malloc(message->nbody+1);
110   - sprintf(message->body, RESP_DATA, uname);
111   - //memcpy(message->body, RESP_DATA, sizeof(RESP_DATA)-1);
112   -
113   - return response;
114   -}
115   -
116   -// vim: set ts=4 sw=4:
... ... @@ -34,6 +34,7 @@
34 34 #include "http/header.h"
35 35
36 36 #include "utils/memory.h"
  37 +#include "hash.h"
37 38
38 39 #define RESP_DATA "{\"ctime\":%ld,\"vnext\":%ld,\"value\":\"%02d\"}"
39 40
... ... @@ -49,7 +50,7 @@ httpResponseRandval(time_t ctime, int value)
49 50 response = new(HttpResponse, "HTTP/1.1", 200, "OK");
50 51 message = (HttpMessage)response;
51 52
52   - httpHeaderAdd(&(message->header),
  53 + hashAdd(message->header,
53 54 new(HttpHeader, CSTRA("Content-Type"), CSTRA("application/json")));
54 55
55 56 message->type = HTTP_MESSAGE_BUFFERED;
... ...
... ... @@ -35,6 +35,7 @@
35 35 #include "session.h"
36 36
37 37 #include "utils/memory.h"
  38 +#include "hash.h"
38 39
39 40 #define RESP_DATA "{\"id\":\"%lu\",\"timeout\":%d,\"timeleft\":%ld,\"username\":\"%s\"}"
40 41
... ... @@ -49,7 +50,7 @@ httpResponseSession(Session session)
49 50 response = new(HttpResponse, "HTTP/1.1", 200, "OK");
50 51 message = (HttpMessage)response;
51 52
52   - httpHeaderAdd(&(message->header),
  53 + hashAdd(message->header,
53 54 new(HttpHeader, CSTRA("Content-Type"), CSTRA("application/json")));
54 55
55 56 message->type = HTTP_MESSAGE_BUFFERED;
... ...
... ... @@ -5,9 +5,11 @@
5 5 #include "interface/class.h"
6 6
7 7 #include "http/message.h"
  8 +#include "http/header.h"
8 9 #include "http/response.h"
9 10
10 11 #include "utils/memory.h"
  12 +#include "hash.h"
11 13
12 14 void
13 15 httpWorkerAddCommonHeader(HttpMessage request, HttpMessage response)
... ... @@ -18,17 +20,15 @@ httpWorkerAddCommonHeader(HttpMessage request, HttpMessage response)
18 20 size_t nbuf;
19 21
20 22 if (httpMessageHasKeepAlive(request)) {
21   - httpHeaderAdd(
22   - &(response->header),
  23 + hashAdd(response->header,
23 24 new(HttpHeader, CSTRA("Connection"), CSTRA("Keep-Alive")));
24 25 }
25 26 else {
26   - httpHeaderAdd(
27   - &(response->header),
  27 + hashAdd(response->header,
28 28 new(HttpHeader, CSTRA("Connection"), CSTRA("Close")));
29 29 }
30 30
31   - httpHeaderAdd(&(response->header),
  31 + hashAdd(response->header,
32 32 new(HttpHeader, CSTRA("Server"), CSTRA("testserver")));
33 33
34 34 switch(((HttpResponse)response)->status) {
... ... @@ -37,14 +37,14 @@ httpWorkerAddCommonHeader(HttpMessage request, HttpMessage response)
37 37
38 38 default:
39 39 nbuf = sprintf(buffer, "%d", response->nbody);
40   - httpHeaderAdd(&(response->header),
  40 + hashAdd(response->header,
41 41 new(HttpHeader, CSTRA("Content-Length"), buffer, nbuf));
42 42 }
43 43
44 44 t = time(NULL);
45 45 tmp = localtime(&t);
46 46 nbuf = strftime(buffer, sizeof(buffer), "%a, %d %b %Y %T %Z", tmp);
47   - httpHeaderAdd(&(response->header),
  47 + hashAdd(response->header,
48 48 new(HttpHeader, CSTRA("Date"), buffer, nbuf));
49 49 }
50 50
... ...
... ... @@ -6,6 +6,7 @@
6 6 #include "http/response.h"
7 7
8 8 #include "utils/memory.h"
  9 +#include "hash.h"
9 10
10 11 HttpMessage
11 12 httpWorkerGetAsset(
... ... @@ -18,8 +19,8 @@ httpWorkerGetAsset(
18 19 size_t nmatch;
19 20 HttpHeader header;
20 21
21   - header = httpHeaderGet(
22   - &(((HttpMessage)request)->header),
  22 + header = hashGet(
  23 + ((HttpMessage)request)->header,
23 24 CSTRA("If-None-Match"));
24 25
25 26 if (NULL == header) {
... ...
... ... @@ -30,6 +30,7 @@
30 30 #include "interface/class.h"
31 31
32 32 #include "http/worker.h"
  33 +#include "http/header.h"
33 34 #include "http/message.h"
34 35 #include "http/request.h"
35 36 #include "http/response.h"
... ... @@ -39,6 +40,7 @@
39 40 #include "stream.h"
40 41
41 42 #include "utils/memory.h"
  43 +#include "hash.h"
42 44
43 45 HttpMessage httpWorkerGetAsset(HttpRequest, const char *, const char *, size_t);
44 46 void httpWorkerAddCommonHeader(HttpMessage, HttpMessage);
... ... @@ -60,8 +62,8 @@ httpWorkerProcess(HttpWorker this, Stream st)
60 62 HttpMessage rmessage = reqq->msgs[i];
61 63 HttpRequest request = (HttpRequest)(reqq->msgs[i]);
62 64 HttpMessage response = NULL;
63   - HttpHeader cookie = httpHeaderGet(
64   - &(rmessage->header),
  65 + HttpHeader cookie = hashGet(
  66 + rmessage->header,
65 67 CSTRA("cookie"));
66 68
67 69 if (NULL == this->session && NULL != cookie) {
... ... @@ -111,8 +113,7 @@ httpWorkerProcess(HttpWorker this, Stream st)
111 113
112 114 response = (HttpMessage)httpResponseSession(this->session);
113 115
114   - httpHeaderAdd(
115   - &(response->header),
  116 + hashAdd(response->header,
116 117 new(HttpHeader, CSTRA("Set-Cookie"), buffer, nbuf));
117 118 }
118 119 }
... ...
1 1 /**
2 2 * \file
3   - * Get a header from a tree containing headers by its name.
4   - * The key for the tree is the hased lowercase header identifier.
5 3 *
6 4 * \author Georg Hopp
7 5 *
8 6 * \copyright
9   - * Copyright (C) 2012 Georg Hopp
  7 + * Copyright © 2012 Georg Hopp
10 8 *
11 9 * This program is free software: you can redistribute it and/or modify
12 10 * it under the terms of the GNU General Public License as published by
... ... @@ -22,30 +20,32 @@
22 20 * along with this program. If not, see <http://www.gnu.org/licenses/>.
23 21 */
24 22
25   -#include <search.h>
26 23 #include <stdlib.h>
  24 +#include <stdio.h>
  25 +#include <stdarg.h>
27 26
28   -#include "http/header.h"
29   -#include "utils/hash.h"
  27 +#include "class.h"
  28 +#include "interface/hashable.h"
30 29
31   -static
32   -inline
33   -int
34   -comp(const void * _a, const void * _b)
35   -{
36   - const unsigned long * a = _a;
37   - HttpHeader b = (HttpHeader)_b;
38   - return (*a < b->hash)? -1 : (*a > b->hash)? 1 : 0;
39   -}
  30 +const struct interface i_Hashable = {
  31 + "hashable",
  32 + 2
  33 +};
40 34
41   -HttpHeader
42   -httpHeaderGet(const HttpHeader * root, const char * name, size_t nname)
  35 +unsigned long
  36 +hashableGetHash(void * hashable)
43 37 {
44   - unsigned long hash = sdbm((const unsigned char*)name, nname);
  38 + unsigned long ret;
45 39
46   - HttpHeader * found = tfind(&hash, (void**)root, comp);
  40 + RETCALL(hashable, Hashable, getHash, ret);
47 41
48   - return (NULL != found)? *found : NULL;
  42 + return ret;
  43 +}
  44 +
  45 +void
  46 +hashableHandleDouble(void * hashable, void * new_hashable)
  47 +{
  48 + CALL(hashable, Hashable, handleDouble, new_hashable);
49 49 }
50 50
51 51 // vim: set ts=4 sw=4:
... ...
Please register or login to post a comment