Commit f2dbad19c684012a6ac235a253349ffe049668db
1 parent
45b4b354
another try with a shared memory based ringbuffer...this performs well for keep-…
…alive sessions but is much slower without. actually i am not sure why but most likely the shared memory setup is quite expensive. @TODO: make a profiling.
Showing
35 changed files
with
557 additions
and
223 deletions
1 | -2012-02-18 20:12:27 +0100 Georg Hopp | 1 | +2012-02-19 11:35:15 +0100 Georg Hopp |
2 | 2 | ||
3 | - * lots of changes but primarily change the request parser to use a ringbuffer. The ringbuffer is implemented using the shared memory trick. (HEAD, master) | 3 | + * another try with a shared memory based ringbuffer...this performs well for keep-alive sessions but is much slower without. actually i am not sure why but most likely the shared memory setup is quite expensive. @TODO: make a profiling. (HEAD, ringbuffer) |
4 | 4 | ||
5 | 2012-02-15 12:30:33 +0100 Georg Hopp | 5 | 2012-02-15 12:30:33 +0100 Georg Hopp |
6 | 6 | ||
7 | - * some more cleanups in the server code. Removing not needed header includes (origin/master, origin/HEAD) | 7 | + * some more cleanups in the server code. Removing not needed header includes |
8 | 8 | ||
9 | 2012-02-15 12:17:39 +0100 Georg Hopp | 9 | 2012-02-15 12:17:39 +0100 Georg Hopp |
10 | 10 |
@@ -4,9 +4,10 @@ | @@ -4,9 +4,10 @@ | ||
4 | #include "class.h" | 4 | #include "class.h" |
5 | #include "http/request.h" | 5 | #include "http/request.h" |
6 | #include "http/message/queue.h" | 6 | #include "http/message/queue.h" |
7 | -#include "ringbuffer.h" | 7 | +#include "cbuf.h" |
8 | + | ||
9 | +#define HTTP_REQUEST_PARSER_BUFFER_MAX 8192 | ||
8 | 10 | ||
9 | -#define HTTP_REQUEST_PARSER_MAX_BUF 131072 | ||
10 | 11 | ||
11 | /** | 12 | /** |
12 | * limits to stop invalid requests from killing | 13 | * limits to stop invalid requests from killing |
@@ -31,7 +32,7 @@ typedef enum e_HttpRequestState { | @@ -31,7 +32,7 @@ typedef enum e_HttpRequestState { | ||
31 | 32 | ||
32 | 33 | ||
33 | CLASS(HttpRequestParser) { | 34 | CLASS(HttpRequestParser) { |
34 | - Ringbuffer buffer; | 35 | + Cbuf buffer; |
35 | 36 | ||
36 | HttpMessageQueue request_queue; | 37 | HttpMessageQueue request_queue; |
37 | HttpRequest cur_request; | 38 | HttpRequest cur_request; |
@@ -41,6 +42,7 @@ CLASS(HttpRequestParser) { | @@ -41,6 +42,7 @@ CLASS(HttpRequestParser) { | ||
41 | 42 | ||
42 | ssize_t httpRequestParserRead(HttpRequestParser, int); | 43 | ssize_t httpRequestParserRead(HttpRequestParser, int); |
43 | ssize_t httpRequestParserParse(HttpRequestParser, int); | 44 | ssize_t httpRequestParserParse(HttpRequestParser, int); |
45 | +void httpRequestParserGetBody(HttpRequestParser); | ||
44 | 46 | ||
45 | ssize_t httpRequestParserGetRequestLine(HttpRequestParser, char *); | 47 | ssize_t httpRequestParserGetRequestLine(HttpRequestParser, char *); |
46 | ssize_t httpRequestParserGetHeader(HttpRequestParser, char *); | 48 | ssize_t httpRequestParserGetHeader(HttpRequestParser, char *); |
1 | #ifndef __HTTP_RESPONSE_WRITER_H__ | 1 | #ifndef __HTTP_RESPONSE_WRITER_H__ |
2 | #define __HTTP_RESPONSE_WRITER_H__ | 2 | #define __HTTP_RESPONSE_WRITER_H__ |
3 | 3 | ||
4 | +#include <sys/types.h> | ||
5 | + | ||
4 | #include "class.h" | 6 | #include "class.h" |
5 | #include "http/response.h" | 7 | #include "http/response.h" |
6 | #include "http/message/queue.h" | 8 | #include "http/message/queue.h" |
9 | +#include "cbuf.h" | ||
7 | 10 | ||
8 | #define RESPONSE_WRITER_MAX_BUF 131072 | 11 | #define RESPONSE_WRITER_MAX_BUF 131072 |
9 | 12 | ||
@@ -15,17 +18,15 @@ typedef enum e_HttpResponseState { | @@ -15,17 +18,15 @@ typedef enum e_HttpResponseState { | ||
15 | } HttpResponseState; | 18 | } HttpResponseState; |
16 | 19 | ||
17 | CLASS(HttpResponseWriter) { | 20 | CLASS(HttpResponseWriter) { |
18 | - char * pipe; | ||
19 | - | ||
20 | - size_t nheader; | ||
21 | - size_t nbuffer; | ||
22 | - size_t written; | ||
23 | - size_t pstart; | ||
24 | - size_t pend; | 21 | + Cbuf buffer; |
25 | 22 | ||
26 | HttpMessageQueue response_queue; | 23 | HttpMessageQueue response_queue; |
27 | HttpResponse cur_response; | 24 | HttpResponse cur_response; |
28 | 25 | ||
26 | + size_t nheader; | ||
27 | + size_t nbody; | ||
28 | + size_t written; | ||
29 | + | ||
29 | HttpResponseState state; | 30 | HttpResponseState state; |
30 | }; | 31 | }; |
31 | 32 |
@@ -8,8 +8,7 @@ | @@ -8,8 +8,7 @@ | ||
8 | #include "http/response/writer.h" | 8 | #include "http/response/writer.h" |
9 | 9 | ||
10 | CLASS(HttpWorker) { | 10 | CLASS(HttpWorker) { |
11 | - char * remoteAddr; | ||
12 | - int handle; | 11 | + char * id; |
13 | 12 | ||
14 | HttpRequestParser parser; | 13 | HttpRequestParser parser; |
15 | HttpResponseWriter writer; | 14 | HttpResponseWriter writer; |
@@ -15,7 +15,7 @@ CLASS(Sock) { | @@ -15,7 +15,7 @@ CLASS(Sock) { | ||
15 | 15 | ||
16 | void socketConnect(Sock this, const char * addr); | 16 | void socketConnect(Sock this, const char * addr); |
17 | void socketListen(Sock this, int backlog); | 17 | void socketListen(Sock this, int backlog); |
18 | -Sock socketAccept(Sock this, char (*remoteAddr)[]); | 18 | +Sock socketAccept(Sock this, char (*remoteAddr)[16]); |
19 | 19 | ||
20 | #endif // __SOCKET_H__ | 20 | #endif // __SOCKET_H__ |
21 | 21 |
@@ -9,6 +9,11 @@ RB = ringbuffer.c ringbuffer/rb_read.c | @@ -9,6 +9,11 @@ RB = ringbuffer.c ringbuffer/rb_read.c | ||
9 | SOCKET = socket.c socket/accept.c socket/connect.c socket/listen.c | 9 | SOCKET = socket.c socket/accept.c socket/connect.c socket/listen.c |
10 | SERVER = server.c server/run.c server/close_conn.c | 10 | SERVER = server.c server/run.c server/close_conn.c |
11 | LOGGER = logger.c logger/stderr.c logger/syslog.c | 11 | LOGGER = logger.c logger/stderr.c logger/syslog.c |
12 | +CB = cbuf.c cbuf/read.c cbuf/write.c \ | ||
13 | + cbuf/get_line.c cbuf/set_data.c cbuf/get_data.c \ | ||
14 | + cbuf/addr_index.c cbuf/get_free.c cbuf/get_read.c cbuf/get_write.c \ | ||
15 | + cbuf/inc_read.c cbuf/inc_write.c cbuf/is_empty.c cbuf/memchr.c \ | ||
16 | + cbuf/skip_non_alpha.c | ||
12 | MSG = http/message.c http/message/queue.c http/message/has_keep_alive.c \ | 17 | MSG = http/message.c http/message/queue.c http/message/has_keep_alive.c \ |
13 | http/message/header_size_get.c http/message/header_to_string.c | 18 | http/message/header_size_get.c http/message/header_to_string.c |
14 | REQ = http/request.c | 19 | REQ = http/request.c |
@@ -31,7 +36,7 @@ bin_PROGRAMS = testserver | @@ -31,7 +36,7 @@ bin_PROGRAMS = testserver | ||
31 | 36 | ||
32 | testserver_SOURCES = testserver.c \ | 37 | testserver_SOURCES = testserver.c \ |
33 | $(IFACE) $(CLASS) $(SOCKET) $(SERVER) $(LOGGER) $(MSG) $(REQ) \ | 38 | $(IFACE) $(CLASS) $(SOCKET) $(SERVER) $(LOGGER) $(MSG) $(REQ) \ |
34 | - $(WRITER) $(RESP) $(HEADER) $(PARSER) $(WORKER) $(RB) \ | 39 | + $(WRITER) $(RESP) $(HEADER) $(PARSER) $(WORKER) $(CB) \ |
35 | signalHandling.c daemonize.c | 40 | signalHandling.c daemonize.c |
36 | testserver_CFLAGS = -Wall -I ../include/ | 41 | testserver_CFLAGS = -Wall -I ../include/ |
37 | testserver_LDFLAGS = -lrt | 42 | testserver_LDFLAGS = -lrt |
src/cbuf.c
0 → 100644
1 | +#define _POSIX_SOURCE | ||
2 | +#define _POSIX_C_SOURCE 200112L | ||
3 | + | ||
4 | +#include <sys/types.h> | ||
5 | +#include <sys/stat.h> | ||
6 | +#include <sys/mman.h> | ||
7 | +#include <stdarg.h> | ||
8 | +#include <stdlib.h> | ||
9 | +#include <stdio.h> | ||
10 | +#include <unistd.h> | ||
11 | +#include <fcntl.h> | ||
12 | + | ||
13 | +#include "class.h" | ||
14 | +#include "interface/class.h" | ||
15 | + | ||
16 | +#include "cbuf.h" | ||
17 | + | ||
18 | + | ||
19 | +static void dtor(void*); | ||
20 | + | ||
21 | +static | ||
22 | +void | ||
23 | +ctor(void * _this, va_list * params) | ||
24 | +{ | ||
25 | + Cbuf this = _this; | ||
26 | + char state = 0; | ||
27 | + char * shm_name = va_arg(*params, char*); | ||
28 | + long psize = sysconf(_SC_PAGESIZE); | ||
29 | + size_t size; | ||
30 | + int shm; | ||
31 | + | ||
32 | + this->shm_name = malloc(strlen(shm_name) + 7 + 2); | ||
33 | + sprintf(this->shm_name, "/%06d_%s", getpid(), shm_name); | ||
34 | + | ||
35 | + /** | ||
36 | + * align size at page boundary. | ||
37 | + * increase as neccessary | ||
38 | + */ | ||
39 | + size = va_arg(*params, size_t); | ||
40 | + size = (0 >= size)? 1 : (0 != size%psize)? (size/psize)+1 : size/psize; | ||
41 | + this->bsize = psize * size; | ||
42 | + | ||
43 | + while (0 == state) { | ||
44 | + shm = shm_open(this->shm_name, O_RDWR|O_CREAT|O_EXCL, S_IRWXU); | ||
45 | + if (-1 == shm) { | ||
46 | + break; | ||
47 | + } | ||
48 | + | ||
49 | + if (-1 == ftruncate(shm, this->bsize)) { | ||
50 | + break; | ||
51 | + } | ||
52 | + | ||
53 | + this->data = mmap (0, this->bsize << 1, | ||
54 | + PROT_READ|PROT_WRITE, MAP_SHARED, shm, 0); | ||
55 | + if (this->data == MAP_FAILED) { | ||
56 | + this->data = NULL; | ||
57 | + break; | ||
58 | + } | ||
59 | + | ||
60 | + munmap(this->data + this->bsize, this->bsize); | ||
61 | + | ||
62 | + this->mirror = mmap (this->data + this->bsize, this->bsize, | ||
63 | + PROT_READ|PROT_WRITE, MAP_SHARED, shm, 0); | ||
64 | + if (this->mirror != this->data + this->bsize) { | ||
65 | + if (this->mirror == this->data - this->bsize) { | ||
66 | + this->data = this->mirror; | ||
67 | + this->mirror += this->bsize; | ||
68 | + } | ||
69 | + else { | ||
70 | + this->mirror = NULL; | ||
71 | + break; | ||
72 | + } | ||
73 | + } | ||
74 | + | ||
75 | + state = 1; | ||
76 | + } | ||
77 | + | ||
78 | + if (-1 != shm) { | ||
79 | + shm_unlink(this->shm_name); | ||
80 | + close(shm); | ||
81 | + } | ||
82 | + | ||
83 | + if (1 != state) { | ||
84 | + dtor(this); | ||
85 | + } | ||
86 | +} | ||
87 | + | ||
88 | +static | ||
89 | +void | ||
90 | +dtor(void * _this) | ||
91 | +{ | ||
92 | + Cbuf this = _this; | ||
93 | + | ||
94 | + if (NULL != this->shm_name) { | ||
95 | + free(this->shm_name); | ||
96 | + this->shm_name = NULL; | ||
97 | + } | ||
98 | + | ||
99 | + if (NULL != this->data) { | ||
100 | + munmap(this->data, this->bsize); | ||
101 | + this->data = NULL; | ||
102 | + } | ||
103 | + | ||
104 | + if (NULL != this->mirror) { | ||
105 | + munmap(this->mirror, this->bsize); | ||
106 | + this->mirror = NULL; | ||
107 | + } | ||
108 | +} | ||
109 | + | ||
110 | +INIT_IFACE(Class, ctor, dtor, NULL); | ||
111 | +CREATE_CLASS(Cbuf, NULL, IFACE(Class)); | ||
112 | + | ||
113 | +// vim: set ts=4 sw=4: |
src/cbuf/addr_index.c
0 → 100644
src/cbuf/get_data.c
0 → 100644
1 | +#include <sys/types.h> | ||
2 | +#include <string.h> | ||
3 | + | ||
4 | +#include "cbuf.h" | ||
5 | + | ||
6 | +char * | ||
7 | +cbufGetData(Cbuf this, size_t n) | ||
8 | +{ | ||
9 | + char * ret = cbufGetRead(this); | ||
10 | + | ||
11 | + if (n > this->bused) { | ||
12 | + return -1; | ||
13 | + } | ||
14 | + | ||
15 | + cbufIncRead(this, n); | ||
16 | + return ret; | ||
17 | +} | ||
18 | + | ||
19 | +// vim: set ts=4 sw=4: |
src/cbuf/get_free.c
0 → 100644
src/cbuf/get_line.c
0 → 100644
1 | +#include <sys/types.h> | ||
2 | + | ||
3 | +#include <string.h> | ||
4 | + | ||
5 | +#include "cbuf.h" | ||
6 | + | ||
7 | +char * | ||
8 | +cbufGetLine(Cbuf this) | ||
9 | +{ | ||
10 | + char * nl = cbufMemchr(this, '\n'); | ||
11 | + char * ret = NULL; | ||
12 | + | ||
13 | + if (NULL != nl) { | ||
14 | + size_t len = cbufAddrIndex(this, nl) + 1; | ||
15 | + | ||
16 | + *nl = 0; | ||
17 | + *(nl-1) = ('\r' == *(nl-1))? 0 : *(nl-1); | ||
18 | + | ||
19 | + ret = cbufGetRead(this); | ||
20 | + cbufIncRead(this, len); | ||
21 | + } | ||
22 | + | ||
23 | + return ret; | ||
24 | +} | ||
25 | + | ||
26 | +// vim: set ts=4 sw=4: |
src/cbuf/get_read.c
0 → 100644
src/cbuf/get_write.c
0 → 100644
src/cbuf/inc_read.c
0 → 100644
src/cbuf/inc_write.c
0 → 100644
src/cbuf/is_empty.c
0 → 100644
src/cbuf/memchr.c
0 → 100644
src/cbuf/read.c
0 → 100644
1 | +#include <sys/types.h> | ||
2 | +#include <unistd.h> | ||
3 | +#include <errno.h> | ||
4 | + | ||
5 | +#include "cbuf.h" | ||
6 | + | ||
7 | + | ||
8 | +ssize_t | ||
9 | +cbufRead(Cbuf this, int fd) | ||
10 | +{ | ||
11 | + ssize_t rrsize = 0; | ||
12 | + size_t rsize = cbufGetFree(this); | ||
13 | + | ||
14 | + if (0 == rsize) { | ||
15 | + errno = ECBUFOVFL; | ||
16 | + return -1; | ||
17 | + } | ||
18 | + | ||
19 | + rrsize = read(fd, cbufGetWrite(this), rsize); | ||
20 | + | ||
21 | + switch (rrsize) { | ||
22 | + case 0: | ||
23 | + rrsize = -2; | ||
24 | + // DROP THROUGH | ||
25 | + | ||
26 | + case -1: | ||
27 | + break; | ||
28 | + | ||
29 | + default: | ||
30 | + cbufIncWrite(this, rrsize); | ||
31 | + break; | ||
32 | + } | ||
33 | + | ||
34 | + return rrsize; | ||
35 | +} | ||
36 | + | ||
37 | +// vim: set ts=4 sw=4: |
src/cbuf/set_data.c
0 → 100644
1 | +#include <sys/types.h> | ||
2 | +#include <string.h> | ||
3 | +#include <errno.h> | ||
4 | + | ||
5 | +#include "cbuf.h" | ||
6 | + | ||
7 | +char * | ||
8 | +cbufSetData(Cbuf this, const void * src, size_t n) | ||
9 | +{ | ||
10 | + char * addr; | ||
11 | + | ||
12 | + if (n > cbufGetFree(this)) { | ||
13 | + errno = ECBUFOVFL; | ||
14 | + return -1; | ||
15 | + } | ||
16 | + | ||
17 | + addr = memcpy(cbufGetWrite(this), src, n); | ||
18 | + cbufIncWrite(this, n); | ||
19 | + | ||
20 | + return addr; | ||
21 | +} | ||
22 | + | ||
23 | +// vim: set ts=4 sw=4: |
src/cbuf/skip_non_alpha.c
0 → 100644
src/cbuf/write.c
0 → 100644
1 | +#include <sys/types.h> | ||
2 | +#include <unistd.h> | ||
3 | + | ||
4 | +#include "cbuf.h" | ||
5 | + | ||
6 | + | ||
7 | +ssize_t | ||
8 | +cbufWrite(Cbuf this, int fd) | ||
9 | +{ | ||
10 | + ssize_t wwsize = 0; | ||
11 | + size_t wsize = this->bused; | ||
12 | + | ||
13 | + if (0 == wsize) return 0; | ||
14 | + | ||
15 | + wwsize = write(fd, cbufGetRead(this), wsize); | ||
16 | + | ||
17 | + switch (wwsize) { | ||
18 | + case -1: | ||
19 | + break; | ||
20 | + | ||
21 | + default: | ||
22 | + cbufIncRead(this, wwsize); | ||
23 | + break; | ||
24 | + } | ||
25 | + | ||
26 | + return wwsize; | ||
27 | +} | ||
28 | + | ||
29 | +// vim: set ts=4 sw=4: |
1 | #include <unistd.h> | 1 | #include <unistd.h> |
2 | -#include <string.h> | 2 | +#include <stdio.h> |
3 | #include <stdlib.h> | 3 | #include <stdlib.h> |
4 | #include <sys/types.h> | 4 | #include <sys/types.h> |
5 | 5 | ||
@@ -10,17 +10,20 @@ | @@ -10,17 +10,20 @@ | ||
10 | #include "http/request/parser.h" | 10 | #include "http/request/parser.h" |
11 | #include "http/message/queue.h" | 11 | #include "http/message/queue.h" |
12 | #include "http/request.h" | 12 | #include "http/request.h" |
13 | -#include "ringbuffer.h" | 13 | +#include "cbuf.h" |
14 | 14 | ||
15 | 15 | ||
16 | static | 16 | static |
17 | void | 17 | void |
18 | ctor(void * _this, va_list * params) | 18 | ctor(void * _this, va_list * params) |
19 | { | 19 | { |
20 | - HttpRequestParser this = _this; | ||
21 | - char * shm_name = va_arg(*params, char*); | 20 | + HttpRequestParser this = _this; |
21 | + char * id = va_arg(*params, char*); | ||
22 | + char cbuf_id[100]; | ||
23 | + | ||
24 | + sprintf(cbuf_id, "%s_%s", "parser", id); | ||
22 | 25 | ||
23 | - this->buffer = new(Ringbuffer, shm_name, HTTP_REQUEST_LINE_MAX); | 26 | + this->buffer = new(Cbuf, cbuf_id, HTTP_REQUEST_PARSER_BUFFER_MAX); |
24 | this->request_queue = new(HttpMessageQueue); | 27 | this->request_queue = new(HttpMessageQueue); |
25 | } | 28 | } |
26 | 29 | ||
@@ -37,9 +40,8 @@ dtor(void * _this) | @@ -37,9 +40,8 @@ dtor(void * _this) | ||
37 | delete(&(this->cur_request)); | 40 | delete(&(this->cur_request)); |
38 | } | 41 | } |
39 | 42 | ||
40 | - | ||
41 | INIT_IFACE(Class, ctor, dtor, NULL); | 43 | INIT_IFACE(Class, ctor, dtor, NULL); |
42 | -INIT_IFACE(StreamReader, (fptr_streamReaderRead)httpRequestParserParse); | 44 | +INIT_IFACE(StreamReader, (fptr_streamReaderRead)httpRequestParserRead); |
43 | CREATE_CLASS(HttpRequestParser, NULL, IFACE(Class), IFACE(StreamReader)); | 45 | CREATE_CLASS(HttpRequestParser, NULL, IFACE(Class), IFACE(StreamReader)); |
44 | 46 | ||
45 | // vim: set ts=4 sw=4: | 47 | // vim: set ts=4 sw=4: |
@@ -3,6 +3,10 @@ | @@ -3,6 +3,10 @@ | ||
3 | #include "http/header.h" | 3 | #include "http/header.h" |
4 | #include "http/message.h" | 4 | #include "http/message.h" |
5 | #include "http/request/parser.h" | 5 | #include "http/request/parser.h" |
6 | +#include "cbuf.h" | ||
7 | + | ||
8 | +#define MAX(a,b) (((a) > (b))? (a) : (b)) | ||
9 | + | ||
6 | 10 | ||
7 | #define MAX(x,y) ((x) > (y) ? (x) : (y)) | 11 | #define MAX(x,y) ((x) > (y) ? (x) : (y)) |
8 | 12 | ||
@@ -14,41 +18,34 @@ void | @@ -14,41 +18,34 @@ void | ||
14 | httpRequestParserGetBody(HttpRequestParser this) | 18 | httpRequestParserGetBody(HttpRequestParser this) |
15 | { | 19 | { |
16 | HttpMessage message = (HttpMessage)(this->cur_request); | 20 | HttpMessage message = (HttpMessage)(this->cur_request); |
17 | - char * str_nbody; | ||
18 | - int nbody; | ||
19 | - int len; | ||
20 | - | ||
21 | - str_nbody = httpHeaderGet( | ||
22 | - &(message->header), | ||
23 | - "Content-Length"); | ||
24 | - | ||
25 | - if (NULL == str_nbody) { | ||
26 | - this->state = HTTP_REQUEST_DONE; | ||
27 | - return -1; | ||
28 | - } | ||
29 | - | ||
30 | - nbody = atoi(str_nbody); | 21 | + size_t len; |
31 | 22 | ||
32 | if (0 == message->nbody) { | 23 | if (0 == message->nbody) { |
33 | - message->type = HTTP_MESSAGE_BUFFERED; | ||
34 | - if (0 < nbody) | ||
35 | - message->body = malloc(nbody); | 24 | + char * nbody = httpHeaderGet( |
25 | + &(message->header), | ||
26 | + "Content-Length"); | ||
27 | + | ||
28 | + if (NULL == nbody) { | ||
29 | + this->state = HTTP_REQUEST_DONE; | ||
30 | + return; | ||
31 | + } | ||
32 | + else { | ||
33 | + message->type = HTTP_MESSAGE_BUFFERED; | ||
34 | + message->nbody = atoi(nbody); | ||
35 | + message->body = calloc(1, message->nbody); | ||
36 | + message->dbody = 0; | ||
37 | + } | ||
36 | } | 38 | } |
39 | + this->buffer->bused -= len; | ||
37 | 40 | ||
38 | - len = MAX(nbody - message->nbody, this->buffer->bused); | ||
39 | - memcpy(message->body + message->nbody, | ||
40 | - this->buffer->buffer + this->buffer->bstart, | ||
41 | - len); | 41 | + if (message->dbody < message->nbody) { |
42 | + len = MAX( | ||
43 | + message->nbody - message->dbody, | ||
44 | + this->buffer->bused); | ||
42 | 45 | ||
43 | - message->nbody += len; | ||
44 | - this->buffer->bstart += len; | ||
45 | - if (this->buffer->bstart >= this->buffer->bsize) { | ||
46 | - this->buffer->bstart -= this->buffer->bsize; | ||
47 | - } | ||
48 | - this->buffer->bused -= len; | 46 | + memcpy(message->body, cbufGetData(this->buffer, len), len); |
49 | 47 | ||
50 | - if (message->nbody == nbody) { | ||
51 | - this->state = HTTP_REQUEST_DONE; | 48 | + message->dbody += len; |
52 | } | 49 | } |
53 | } | 50 | } |
54 | 51 |
@@ -7,81 +7,35 @@ | @@ -7,81 +7,35 @@ | ||
7 | #include "http/message.h" | 7 | #include "http/message.h" |
8 | #include "http/request/parser.h" | 8 | #include "http/request/parser.h" |
9 | #include "interface/class.h" | 9 | #include "interface/class.h" |
10 | - | ||
11 | -#ifndef TRUE | ||
12 | -#define TRUE 1 | ||
13 | -#endif | ||
14 | - | ||
15 | -#ifndef FALSE | ||
16 | -#define FALSE 0 | ||
17 | -#endif | ||
18 | - | ||
19 | -static | ||
20 | -inline | ||
21 | -char * | ||
22 | -getLine(HttpRequestParser this) | ||
23 | -{ | ||
24 | - char * cr = memchr( | ||
25 | - this->buffer->buffer + this->buffer->bstart, | ||
26 | - '\r', | ||
27 | - this->buffer->bused); | ||
28 | - | ||
29 | - char * nl = (NULL == cr)? NULL : cr + 1; | ||
30 | - | ||
31 | - if (NULL != cr && NULL != nl && '\n' == *nl) { | ||
32 | - *cr = 0; | ||
33 | - return cr; | ||
34 | - } | ||
35 | - | ||
36 | - return NULL; | ||
37 | -} | ||
38 | - | ||
39 | -static | ||
40 | -inline | ||
41 | -char | ||
42 | -httpRequestSkip(HttpRequestParser this) | ||
43 | -{ | ||
44 | - while (this->buffer->bused > 0 && | ||
45 | - ! isalpha(this->buffer->buffer[this->buffer->bstart])) { | ||
46 | - this->buffer->bstart = (this->buffer->bstart >= this->buffer->bsize)? | ||
47 | - 0 : this->buffer->bstart + 1; | ||
48 | - this->buffer->bused--; | ||
49 | - } | ||
50 | - | ||
51 | - return (isalpha(this->buffer->buffer[this->buffer->bstart]))? TRUE : FALSE; | ||
52 | -} | 10 | +#include "cbuf.h" |
53 | 11 | ||
54 | ssize_t | 12 | ssize_t |
55 | httpRequestParserParse(HttpRequestParser this, int fd) | 13 | httpRequestParserParse(HttpRequestParser this, int fd) |
56 | { | 14 | { |
57 | int cont = 1; | 15 | int cont = 1; |
58 | - ssize_t ret; | 16 | + ssize_t read; |
17 | + char * line; | ||
59 | 18 | ||
60 | - if (0 > (ret = rbRead(this->buffer, fd))) { | ||
61 | - cont = 0; | 19 | + if(0 > (read = cbufRead(this->buffer, fd))) { |
20 | + return read; | ||
62 | } | 21 | } |
63 | 22 | ||
64 | while (cont) { | 23 | while (cont) { |
65 | switch(this->state) { | 24 | switch(this->state) { |
66 | - char * line_end; | ||
67 | - size_t len; | ||
68 | - | ||
69 | case HTTP_REQUEST_GARBAGE: | 25 | case HTTP_REQUEST_GARBAGE: |
70 | - if (httpRequestSkip(this)) { | 26 | + cbufSkipNonAlpha(this->buffer); |
27 | + if (! cbufIsEmpty(this->buffer)) { | ||
71 | this->cur_request = new(HttpRequest); | 28 | this->cur_request = new(HttpRequest); |
72 | this->state = HTTP_REQUEST_START; | 29 | this->state = HTTP_REQUEST_START; |
73 | } | 30 | } |
74 | - else { | ||
75 | - cont = 0; | ||
76 | - } | ||
77 | break; | 31 | break; |
78 | 32 | ||
79 | case HTTP_REQUEST_START: | 33 | case HTTP_REQUEST_START: |
80 | - if (NULL == (line_end = getLine(this))) { | 34 | + if (NULL == (line = cbufGetLine(this->buffer))) { |
81 | cont = 0; | 35 | cont = 0; |
82 | break; | 36 | break; |
83 | } | 37 | } |
84 | - | 38 | + |
85 | if (0 > httpRequestParserGetRequestLine(this, line_end)) { | 39 | if (0 > httpRequestParserGetRequestLine(this, line_end)) { |
86 | ret = -1; | 40 | ret = -1; |
87 | cont = 0; | 41 | cont = 0; |
@@ -99,7 +53,7 @@ httpRequestParserParse(HttpRequestParser this, int fd) | @@ -99,7 +53,7 @@ httpRequestParserParse(HttpRequestParser this, int fd) | ||
99 | break; | 53 | break; |
100 | 54 | ||
101 | case HTTP_REQUEST_REQUEST_LINE_DONE: | 55 | case HTTP_REQUEST_REQUEST_LINE_DONE: |
102 | - if (NULL == (line_end = getLine(this))) { | 56 | + if (NULL == (line = cbufGetLine(this->buffer))) { |
103 | cont = 0; | 57 | cont = 0; |
104 | break; | 58 | break; |
105 | } | 59 | } |
@@ -127,23 +81,33 @@ httpRequestParserParse(HttpRequestParser this, int fd) | @@ -127,23 +81,33 @@ httpRequestParserParse(HttpRequestParser this, int fd) | ||
127 | break; | 81 | break; |
128 | 82 | ||
129 | case HTTP_REQUEST_HEADERS_DONE: | 83 | case HTTP_REQUEST_HEADERS_DONE: |
130 | - /** | ||
131 | - * allocate memory according to content-length. | ||
132 | - * If content length is to large reject request. | ||
133 | - * | ||
134 | - * @FUTURE check for multipart mime and handle it | ||
135 | - * with temporary file. | ||
136 | - */ | ||
137 | - httpRequestParserGetBody(this); | 84 | + { |
85 | + HttpMessage message = (HttpMessage)this->cur_request; | ||
86 | + | ||
87 | + httpRequestParserGetBody(this); | ||
88 | + | ||
89 | + if (message->dbody == message->nbody) { | ||
90 | + this->state = HTTP_REQUEST_DONE; | ||
91 | + } | ||
92 | + } | ||
138 | break; | 93 | break; |
139 | 94 | ||
140 | case HTTP_REQUEST_DONE: | 95 | case HTTP_REQUEST_DONE: |
141 | this->request_queue->msgs[(this->request_queue->nmsgs)++] = | 96 | this->request_queue->msgs[(this->request_queue->nmsgs)++] = |
142 | (HttpMessage)this->cur_request; | 97 | (HttpMessage)this->cur_request; |
143 | 98 | ||
144 | - ret = this->request_queue->nmsgs; | ||
145 | this->cur_request = NULL; | 99 | this->cur_request = NULL; |
146 | 100 | ||
101 | + /** | ||
102 | + * dont continue loop if input buffer is empty | ||
103 | + */ | ||
104 | + if (cbufIsEmpty(this->buffer)) { | ||
105 | + cont = 0; | ||
106 | + } | ||
107 | + | ||
108 | + /** | ||
109 | + * prepare for next request | ||
110 | + */ | ||
147 | this->state = HTTP_REQUEST_GARBAGE; | 111 | this->state = HTTP_REQUEST_GARBAGE; |
148 | 112 | ||
149 | break; | 113 | break; |
@@ -14,29 +14,46 @@ | @@ -14,29 +14,46 @@ | ||
14 | ssize_t | 14 | ssize_t |
15 | httpRequestParserRead(HttpRequestParser this, int fd) | 15 | httpRequestParserRead(HttpRequestParser this, int fd) |
16 | { | 16 | { |
17 | - size_t rsize; | ||
18 | - ssize_t temp; | ||
19 | - | ||
20 | - this->bend = (this->bsize == this->bend)? | ||
21 | - 0 : this->bend; | ||
22 | - | ||
23 | - rsize = (this->bstart <= this->bend)? | ||
24 | - this->bsize - this->bend : | ||
25 | - this->bstart - 1; | ||
26 | - | ||
27 | - if (0 >= (temp = read(fd, &(this->buffer[this->bend]), rsize))) { | ||
28 | - /** | ||
29 | - * this means either we had an rsize of 0 what indicates that | ||
30 | - * the buffer ran full without any processing took place or | ||
31 | - * the connection was terminated in some way. In both cases | ||
32 | - * we want to terminate the connection. | ||
33 | - */ | ||
34 | - return (0 == temp)? -2 : -1; | ||
35 | - } | ||
36 | - | ||
37 | - this->bend += temp; | ||
38 | - | ||
39 | - return temp; | 17 | + /** |
18 | + * @obsolete | ||
19 | + */ | ||
20 | + return -1; | ||
21 | +// size_t remaining, chunks; | ||
22 | +// char buffer[1024]; | ||
23 | +// | ||
24 | +// ssize_t size = read(fd, buffer, 1024); | ||
25 | +// | ||
26 | +// if (0 < size) { | ||
27 | +// remaining = this->buffer_used % HTTP_REQUEST_PARSER_READ_CHUNK; | ||
28 | +// remaining = HTTP_REQUEST_PARSER_READ_CHUNK - remaining; | ||
29 | +// chunks = this->buffer_used / HTTP_REQUEST_PARSER_READ_CHUNK; | ||
30 | +// | ||
31 | +// /** | ||
32 | +// * because a division always rounds down | ||
33 | +// * chunks holds exactly the currently allocated chunks if | ||
34 | +// * remaining equals 0 but there is no space left. | ||
35 | +// * Else chunks holds the actually allocated amount of chunks | ||
36 | +// * minus 1. | ||
37 | +// * For this reason chunks always has to be increased by 1. | ||
38 | +// */ | ||
39 | +// chunks++; | ||
40 | +// | ||
41 | +// if (size >= remaining) { | ||
42 | +// this->buffer = | ||
43 | +// realloc(this->buffer, chunks * HTTP_REQUEST_PARSER_READ_CHUNK); | ||
44 | +// } | ||
45 | +// | ||
46 | +// memcpy(this->buffer + this->buffer_used, buffer, size); | ||
47 | +// this->buffer_used += size; | ||
48 | +// this->buffer[this->buffer_used] = 0; | ||
49 | +// | ||
50 | +// size = httpRequestParserParse(this); | ||
51 | +// } | ||
52 | +// else { | ||
53 | +// size = (0 == size)? -2 : size; | ||
54 | +// } | ||
55 | +// | ||
56 | +// return size; | ||
40 | } | 57 | } |
41 | 58 | ||
42 | // vim: set ts=4 sw=4: | 59 | // vim: set ts=4 sw=4: |
1 | #include <stdlib.h> | 1 | #include <stdlib.h> |
2 | +#include <stdio.h> | ||
2 | 3 | ||
3 | #include "class.h" | 4 | #include "class.h" |
4 | #include "interface/class.h" | 5 | #include "interface/class.h" |
@@ -12,7 +13,12 @@ void | @@ -12,7 +13,12 @@ void | ||
12 | ctor(void * _this, va_list * params) | 13 | ctor(void * _this, va_list * params) |
13 | { | 14 | { |
14 | HttpResponseWriter this = _this; | 15 | HttpResponseWriter this = _this; |
16 | + char * id = va_arg(*params, char*); | ||
17 | + char cbuf_id[100]; | ||
15 | 18 | ||
19 | + sprintf(cbuf_id, "%s_%s", "writer", id); | ||
20 | + | ||
21 | + this->buffer = new(Cbuf, cbuf_id, RESPONSE_WRITER_MAX_BUF); | ||
16 | this->response_queue = new(HttpMessageQueue); | 22 | this->response_queue = new(HttpMessageQueue); |
17 | } | 23 | } |
18 | 24 | ||
@@ -23,6 +29,7 @@ dtor(void * _this) | @@ -23,6 +29,7 @@ dtor(void * _this) | ||
23 | HttpResponseWriter this = _this; | 29 | HttpResponseWriter this = _this; |
24 | 30 | ||
25 | delete(&(this->response_queue)); | 31 | delete(&(this->response_queue)); |
32 | + delete(&(this->buffer)); | ||
26 | 33 | ||
27 | if (NULL != this->cur_response) | 34 | if (NULL != this->cur_response) |
28 | delete(&(this->cur_response)); | 35 | delete(&(this->cur_response)); |
@@ -11,7 +11,9 @@ | @@ -11,7 +11,9 @@ | ||
11 | #include "http/message.h" | 11 | #include "http/message.h" |
12 | #include "http/response.h" | 12 | #include "http/response.h" |
13 | #include "http/response/writer.h" | 13 | #include "http/response/writer.h" |
14 | +#include "cbuf.h" | ||
14 | 15 | ||
16 | +#define MIN(x,y) ((x) < (y) ? (x) : (y)) | ||
15 | #define MAX(x,y) ((x) > (y) ? (x) : (y)) | 17 | #define MAX(x,y) ((x) > (y) ? (x) : (y)) |
16 | #define _PSIZE(x) (MAX((x),RESPONSE_WRITER_MAX_BUF)) | 18 | #define _PSIZE(x) (MAX((x),RESPONSE_WRITER_MAX_BUF)) |
17 | #define PSIZE _PSIZE(this->nheader+message->nbody) | 19 | #define PSIZE _PSIZE(this->nheader+message->nbody) |
@@ -21,7 +23,6 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | @@ -21,7 +23,6 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | ||
21 | { | 23 | { |
22 | HttpMessageQueue respq = this->response_queue; | 24 | HttpMessageQueue respq = this->response_queue; |
23 | HttpMessage message = (HttpMessage)this->cur_response; | 25 | HttpMessage message = (HttpMessage)this->cur_response; |
24 | - ssize_t processed = (message)? 1 : 0; | ||
25 | int cont = 1; | 26 | int cont = 1; |
26 | 27 | ||
27 | while (cont) { | 28 | while (cont) { |
@@ -30,19 +31,13 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | @@ -30,19 +31,13 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | ||
30 | if (NULL == this->cur_response && 0 < respq->nmsgs) { | 31 | if (NULL == this->cur_response && 0 < respq->nmsgs) { |
31 | message = respq->msgs[0]; | 32 | message = respq->msgs[0]; |
32 | this->cur_response = (HttpResponse)message; | 33 | this->cur_response = (HttpResponse)message; |
33 | - processed++; | ||
34 | 34 | ||
35 | - memmove(respq->msgs, | ||
36 | - &(respq->msgs[1]), | ||
37 | - sizeof(void*) * (--respq->nmsgs + 1)); | ||
38 | - | ||
39 | - this->nbuffer = 0; | ||
40 | this->written = 0; | 35 | this->written = 0; |
41 | - this->pstart = 0; | 36 | + this->nbody = 0; |
42 | this->nheader = httpMessageHeaderSizeGet(message); | 37 | this->nheader = httpMessageHeaderSizeGet(message); |
43 | - this->pend = this->nheader; | ||
44 | - this->pipe = malloc(PSIZE); | ||
45 | - httpMessageHeaderToString(message, this->pipe); | 38 | + |
39 | + httpMessageHeaderToString(message, cbufGetWrite(this->buffer)); | ||
40 | + cbufIncWrite(this->buffer, this->nheader); | ||
46 | 41 | ||
47 | this->state = HTTP_RESPONSE_WRITE; | 42 | this->state = HTTP_RESPONSE_WRITE; |
48 | } | 43 | } |
@@ -55,57 +50,41 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | @@ -55,57 +50,41 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | ||
55 | /** | 50 | /** |
56 | * read | 51 | * read |
57 | */ | 52 | */ |
58 | - if (this->nbuffer < message->nbody) { | ||
59 | - size_t temp = 0; | ||
60 | - size_t rsize; | ||
61 | - | ||
62 | - this->pend = (PSIZE == this->pend)? | ||
63 | - 0 : this->pend; | ||
64 | - | ||
65 | - rsize = (this->pstart <= this->pend)? | ||
66 | - PSIZE - this->pend : | ||
67 | - this->pstart - 1; | 53 | + if (this->nbody < message->nbody) { |
54 | + size_t size = MIN( | ||
55 | + message->nbody - this->nbody, | ||
56 | + cbufGetFree(this->buffer)); | ||
68 | 57 | ||
69 | switch (message->type) { | 58 | switch (message->type) { |
70 | case HTTP_MESSAGE_BUFFERED: | 59 | case HTTP_MESSAGE_BUFFERED: |
71 | - temp = message->nbody - this->nbuffer; | ||
72 | - temp = (rsize<temp)? rsize : temp; | ||
73 | - memcpy( | ||
74 | - &(this->pipe[this->pend]), | ||
75 | - &(message->body[this->nbuffer]), | ||
76 | - temp); | 60 | + cbufSetData(this->buffer, |
61 | + message->body + this->nbody, | ||
62 | + size); | ||
77 | break; | 63 | break; |
78 | 64 | ||
79 | case HTTP_MESSAGE_PIPED: | 65 | case HTTP_MESSAGE_PIPED: |
80 | - temp = read( | ||
81 | - message->handle, | ||
82 | - &(this->pipe[this->pend]), | ||
83 | - rsize); | 66 | + size = cbufRead(this->buffer, message->handle); |
84 | break; | 67 | break; |
68 | + | ||
69 | + default: | ||
70 | + return -1; | ||
85 | } | 71 | } |
86 | 72 | ||
87 | - this->nbuffer += temp; | ||
88 | - this->pend += temp; | 73 | + this->nbody += size; |
89 | } | 74 | } |
90 | 75 | ||
91 | /** | 76 | /** |
92 | * write | 77 | * write |
93 | */ | 78 | */ |
94 | { | 79 | { |
95 | - size_t wsize; | ||
96 | - size_t temp; | ||
97 | - | ||
98 | - wsize = (this->pstart <= this->pend)? | ||
99 | - this->pend - this->pstart : | ||
100 | - PSIZE - this->pstart; | 80 | + ssize_t written = cbufWrite(this->buffer, fd); |
101 | 81 | ||
102 | - temp = write(fd, &(this->pipe[this->pstart]), wsize); | ||
103 | - | ||
104 | - this->written += temp; | ||
105 | - this->pstart += temp; | ||
106 | - | ||
107 | - this->pstart = (PSIZE == this->pstart)? | ||
108 | - 0 : this->pstart; | 82 | + if (0 <= written) { |
83 | + this->written += written; | ||
84 | + } | ||
85 | + else { | ||
86 | + return -1; | ||
87 | + } | ||
109 | } | 88 | } |
110 | 89 | ||
111 | if (this->written == message->nbody + this->nheader) { | 90 | if (this->written == message->nbody + this->nheader) { |
@@ -121,33 +100,30 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | @@ -121,33 +100,30 @@ httpResponseWriterWrite(HttpResponseWriter this, int fd) | ||
121 | close(message->handle); | 100 | close(message->handle); |
122 | } | 101 | } |
123 | 102 | ||
124 | - free(this->pipe); | 103 | + this->state = HTTP_RESPONSE_GET; |
125 | 104 | ||
126 | - this->nheader = 0; | ||
127 | - this->nbuffer = 0; | ||
128 | - this->written = 0; | ||
129 | - this->pstart = 0; | ||
130 | - this->pend = 0; | 105 | + memmove(respq->msgs, |
106 | + &(respq->msgs[1]), | ||
107 | + sizeof(void*) * (--respq->nmsgs + 1)); | ||
131 | 108 | ||
132 | if (! httpMessageHasKeepAlive(message)) { | 109 | if (! httpMessageHasKeepAlive(message)) { |
133 | /** | 110 | /** |
134 | * if the message did not have the keep-alive feature | 111 | * if the message did not have the keep-alive feature |
135 | * we don't care about further pipelined messages and | 112 | * we don't care about further pipelined messages and |
136 | - * return the to caller with a 0 indicating that the | 113 | + * return to the caller with a 0 indicating that the |
137 | * underlying connection should be closed. | 114 | * underlying connection should be closed. |
138 | */ | 115 | */ |
139 | - processed = 0; | ||
140 | - cont = 0; | 116 | + delete(&this->cur_response); |
117 | + return -1; | ||
141 | } | 118 | } |
142 | 119 | ||
143 | delete(&this->cur_response); | 120 | delete(&this->cur_response); |
144 | 121 | ||
145 | - this->state = HTTP_RESPONSE_GET; | ||
146 | break; | 122 | break; |
147 | } | 123 | } |
148 | } | 124 | } |
149 | 125 | ||
150 | - return processed; | 126 | + return respq->nmsgs; |
151 | } | 127 | } |
152 | 128 | ||
153 | // vim: set ts=4 sw=4: | 129 | // vim: set ts=4 sw=4: |
1 | #include <stdlib.h> | 1 | #include <stdlib.h> |
2 | #include <stdarg.h> | 2 | #include <stdarg.h> |
3 | +#include <stdlib.h> | ||
3 | #include <string.h> | 4 | #include <string.h> |
4 | 5 | ||
5 | #include "class.h" | 6 | #include "class.h" |
@@ -17,14 +18,13 @@ void | @@ -17,14 +18,13 @@ void | ||
17 | ctor(void * _this, va_list * params) | 18 | ctor(void * _this, va_list * params) |
18 | { | 19 | { |
19 | HttpWorker this = _this; | 20 | HttpWorker this = _this; |
20 | - char id[sizeof(SHMN) + 15 + 5]; | 21 | + char * id = va_arg(*params, char *); |
21 | 22 | ||
22 | - this->remoteAddr = va_arg(*params, char *); | ||
23 | - this->handle = va_arg(*params, int); | ||
24 | - sprintf(id, SHMN "%s_%05d", this->remoteAddr, this->handle); | 23 | + this->id = malloc(strlen(id) + 1); |
24 | + strcpy(this->id, id); | ||
25 | 25 | ||
26 | - this->parser = new(HttpRequestParser, id); | ||
27 | - this->writer = new(HttpResponseWriter); | 26 | + this->parser = new(HttpRequestParser, this->id); |
27 | + this->writer = new(HttpResponseWriter, this->id); | ||
28 | } | 28 | } |
29 | 29 | ||
30 | static | 30 | static |
@@ -33,6 +33,8 @@ dtor(void * _this) | @@ -33,6 +33,8 @@ dtor(void * _this) | ||
33 | { | 33 | { |
34 | HttpWorker this = _this; | 34 | HttpWorker this = _this; |
35 | 35 | ||
36 | + free(this->id); | ||
37 | + | ||
36 | delete(&this->parser); | 38 | delete(&this->parser); |
37 | delete(&this->writer); | 39 | delete(&this->writer); |
38 | } | 40 | } |
@@ -12,8 +12,6 @@ serverCloseConn(Server this, unsigned int i) | @@ -12,8 +12,6 @@ serverCloseConn(Server this, unsigned int i) | ||
12 | delete(&((this->conns)[fd].sock)); | 12 | delete(&((this->conns)[fd].sock)); |
13 | delete(&((this->conns)[fd].worker)); | 13 | delete(&((this->conns)[fd].worker)); |
14 | 14 | ||
15 | - (this->conns)[fd].keep_alive = 0; | ||
16 | - | ||
17 | memset(&(this->fds[i]), 0, sizeof(struct pollfd)); | 15 | memset(&(this->fds[i]), 0, sizeof(struct pollfd)); |
18 | } | 16 | } |
19 | 17 |
1 | #include <errno.h> | 1 | #include <errno.h> |
2 | +#include <stdio.h> | ||
3 | + | ||
4 | +#include "http/worker.h" | ||
5 | + | ||
2 | 6 | ||
3 | #include "http/worker.h" | 7 | #include "http/worker.h" |
4 | 8 | ||
@@ -12,11 +16,15 @@ serverHandleAccept(Server this) | @@ -12,11 +16,15 @@ serverHandleAccept(Server this) | ||
12 | acc = socketAccept(this->sock, &remoteAddr); | 16 | acc = socketAccept(this->sock, &remoteAddr); |
13 | 17 | ||
14 | if (-1 != acc->handle) { | 18 | if (-1 != acc->handle) { |
19 | + char id[21]; | ||
20 | + | ||
21 | + sprintf(id, "my_%s_%05d", remoteAddr, acc->handle); | ||
22 | + | ||
15 | //* save the socket handle | 23 | //* save the socket handle |
16 | (this->conns)[acc->handle].sock = acc; | 24 | (this->conns)[acc->handle].sock = acc; |
17 | 25 | ||
18 | //* clone reader | 26 | //* clone reader |
19 | - (this->conns)[acc->handle].worker = new(HttpWorker, remoteAddr, acc->handle); | 27 | + (this->conns)[acc->handle].worker = new(HttpWorker, id); |
20 | 28 | ||
21 | (this->fds)[this->nfds].fd = acc->handle; | 29 | (this->fds)[this->nfds].fd = acc->handle; |
22 | (this->fds)[this->nfds].events = POLLIN; | 30 | (this->fds)[this->nfds].events = POLLIN; |
@@ -62,12 +62,12 @@ serverRun(Server this) | @@ -62,12 +62,12 @@ serverRun(Server this) | ||
62 | nreads--; | 62 | nreads--; |
63 | 63 | ||
64 | switch (serverRead(this, i)) { | 64 | switch (serverRead(this, i)) { |
65 | - case -2: | ||
66 | - case -1: | ||
67 | - serverCloseConn(this, i); | 65 | + case 0: |
68 | break; | 66 | break; |
69 | 67 | ||
70 | - case 0: | 68 | + case -1: |
69 | + case -2: | ||
70 | + serverCloseConn(this, i); | ||
71 | break; | 71 | break; |
72 | 72 | ||
73 | default: | 73 | default: |
@@ -80,14 +80,24 @@ serverRun(Server this) | @@ -80,14 +80,24 @@ serverRun(Server this) | ||
80 | * handle writes | 80 | * handle writes |
81 | */ | 81 | */ |
82 | if (0 != ((this->fds)[i].revents & POLLOUT) && 0 < nwrites) { | 82 | if (0 != ((this->fds)[i].revents & POLLOUT) && 0 < nwrites) { |
83 | + size_t remaining; | ||
84 | + | ||
83 | events--; | 85 | events--; |
84 | nwrites--; | 86 | nwrites--; |
85 | 87 | ||
86 | - if (0 >= streamWriterWrite((this->conns)[fd].worker, fd)) { | ||
87 | - serverCloseConn(this, i); | ||
88 | - } | 88 | + remaining = streamWriterWrite((this->conns)[fd].worker, fd); |
89 | + switch(remaining) { | ||
90 | + case -1: | ||
91 | + serverCloseConn(this, i); | ||
92 | + break; | ||
93 | + | ||
94 | + case 0: | ||
95 | + (this->fds)[i].events &= ~POLLOUT; | ||
96 | + break; | ||
89 | 97 | ||
90 | - (this->fds)[i].events &= ~POLLOUT; | 98 | + default: |
99 | + break; | ||
100 | + } | ||
91 | } | 101 | } |
92 | } | 102 | } |
93 | } | 103 | } |
@@ -6,7 +6,7 @@ | @@ -6,7 +6,7 @@ | ||
6 | #include "interface/logger.h" | 6 | #include "interface/logger.h" |
7 | 7 | ||
8 | Sock | 8 | Sock |
9 | -socketAccept(Sock this, char (*remoteAddr)[]) | 9 | +socketAccept(Sock this, char (*remoteAddr)[16]) |
10 | { | 10 | { |
11 | Sock sock; /* Socket for client */ | 11 | Sock sock; /* Socket for client */ |
12 | unsigned int len; /* Length of client address data structure */ | 12 | unsigned int len; /* Length of client address data structure */ |
@@ -33,7 +33,8 @@ socketAccept(Sock this, char (*remoteAddr)[]) | @@ -33,7 +33,8 @@ socketAccept(Sock this, char (*remoteAddr)[]) | ||
33 | loggerLog(this->log, LOGGER_WARNING, | 33 | loggerLog(this->log, LOGGER_WARNING, |
34 | "error accepting connection: %s", strerror(errno)); | 34 | "error accepting connection: %s", strerror(errno)); |
35 | } else { | 35 | } else { |
36 | - memcpy(*remoteAddr, inet_ntoa((sock->addr).sin_addr), 15); | 36 | + strcpy(*remoteAddr, inet_ntoa((sock->addr).sin_addr)); |
37 | + | ||
37 | loggerLog(this->log, LOGGER_INFO, | 38 | loggerLog(this->log, LOGGER_INFO, |
38 | "handling client %s\n", *remoteAddr); | 39 | "handling client %s\n", *remoteAddr); |
39 | } | 40 | } |
@@ -19,8 +19,8 @@ int | @@ -19,8 +19,8 @@ int | ||
19 | main() | 19 | main() |
20 | { | 20 | { |
21 | Logger logger = new(LoggerSyslog, LOGGER_ERR); | 21 | Logger logger = new(LoggerSyslog, LOGGER_ERR); |
22 | - HttpWorker worker = new(HttpWorker, "", 0); | ||
23 | - Server server = new(Server, logger, worker, 11212, SOMAXCONN); | 22 | + //HttpWorker worker = new(HttpWorker); |
23 | + Server server = new(Server, logger, NULL /*worker*/, 11212, SOMAXCONN); | ||
24 | 24 | ||
25 | struct rlimit limit = {RLIM_INFINITY, RLIM_INFINITY}; | 25 | struct rlimit limit = {RLIM_INFINITY, RLIM_INFINITY}; |
26 | setrlimit(RLIMIT_CPU, &limit); | 26 | setrlimit(RLIMIT_CPU, &limit); |
@@ -30,7 +30,7 @@ main() | @@ -30,7 +30,7 @@ main() | ||
30 | serverRun(server); | 30 | serverRun(server); |
31 | 31 | ||
32 | delete(&server); | 32 | delete(&server); |
33 | - delete(&worker); | 33 | +// delete(&worker); |
34 | delete(&logger); | 34 | delete(&logger); |
35 | 35 | ||
36 | return 0; | 36 | return 0; |
Please
register
or
login
to post a comment