Browse Source

- First round of refactoring

decke 6 years ago
parent
commit
ed0fdae57b
7 changed files with 336 additions and 175 deletions
  1. 1
    1
      Makefile
  2. 67
    0
      client.h
  3. 51
    0
      common.c
  4. 32
    0
      common.h
  5. 30
    174
      server.c
  6. 37
    0
      server.h
  7. 118
    0
      stomp.c

+ 1
- 1
Makefile View File

@@ -7,7 +7,7 @@ LOCALBASE?=/usr/local
7 7
 CPPFLAGS=-I${LOCALBASE}/include -g -Wall
8 8
 LDFLAGS=-L${LOCALBASE}/lib -L${LOCALBASE}/lib/event2
9 9
 
10
-SRC =	server.c
10
+SRC =	server.c common.c stomp.c
11 11
 OBJS =	${SRC:.c=.o}
12 12
 
13 13
 all:	redqueue

+ 67
- 0
client.h View File

@@ -0,0 +1,67 @@
1
+/*
2
+ * Copyright (C) 2011 Bernhard Froehlich <decke@bluelife.at>
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ *
9
+ * 1. Redistributions of source code must retain the above copyright
10
+ *    notice, this list of conditions and the following disclaimer.
11
+ * 2. Author's name may not be used endorse or promote products derived
12
+ *    from this software without specific prior written permission.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
18
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23
+ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ * POSSIBILITY OF SUCH DAMAGE.
25
+ */
26
+
27
+#ifndef _CLIENT_H_
28
+#define _CLIENT_H_
29
+
30
+#include <sys/queue.h>
31
+
32
+/**
33
+ * A struct for client specific data, also includes
34
+ * pointer to create a list of clients.
35
+ */
36
+struct client {
37
+   /* The clients socket. */
38
+   int fd;
39
+
40
+   /* The bufferedevent for this client. */
41
+   struct bufferevent *buf_in;
42
+
43
+   /* The output buffer for this client. */
44
+   struct evbuffer *buf_out;
45
+
46
+   /* Plain request */
47
+   char *request;
48
+
49
+   /* Parsed Headers */
50
+   struct evkeyvalq *headers;
51
+
52
+   TAILQ_ENTRY(client) entries;
53
+};
54
+
55
+TAILQ_HEAD(, client) clients;
56
+
57
+
58
+struct queue {
59
+   char *queuename;
60
+
61
+   TAILQ_HEAD(, client) subscribers;
62
+   TAILQ_ENTRY(queue) entries;
63
+};
64
+
65
+TAILQ_HEAD(, queue) queues;
66
+ 
67
+#endif /* _CLIENT_H_ */

+ 51
- 0
common.c View File

@@ -0,0 +1,51 @@
1
+/*
2
+ * Copyright (C) 2011 Bernhard Froehlich <decke@bluelife.at>
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ *
9
+ * 1. Redistributions of source code must retain the above copyright
10
+ *    notice, this list of conditions and the following disclaimer.
11
+ * 2. Author's name may not be used endorse or promote products derived
12
+ *    from this software without specific prior written permission.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
18
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23
+ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ * POSSIBILITY OF SUCH DAMAGE.
25
+ */
26
+
27
+#include <string.h>
28
+#include <sys/queue.h>
29
+
30
+#include <event2/buffer.h>
31
+
32
+#include "common.h"
33
+#include "client.h"
34
+
35
+int find_readers(char *queuename, struct evbuffer *evb)
36
+{
37
+   struct queue *entry, *tmp_entry;
38
+   char buf[MAX_BUF];
39
+
40
+   *buf = '\0';
41
+   for (entry = TAILQ_FIRST(&queues); entry != NULL; entry = tmp_entry) {
42
+      tmp_entry = TAILQ_NEXT(entry, entries);
43
+      if (strncmp(queuename, entry->queuename, strlen(entry->queuename)) == 0){
44
+         evbuffer_add_printf(evb, "queue: %s", queuename);
45
+         //TAILQ_REMOVE(&readers, entry, entries);
46
+         return 1;
47
+      }
48
+   }
49
+   return 0;
50
+}
51
+

+ 32
- 0
common.h View File

@@ -0,0 +1,32 @@
1
+/*
2
+ * Copyright (C) 2011 Bernhard Froehlich <decke@bluelife.at>
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ *
9
+ * 1. Redistributions of source code must retain the above copyright
10
+ *    notice, this list of conditions and the following disclaimer.
11
+ * 2. Author's name may not be used endorse or promote products derived
12
+ *    from this software without specific prior written permission.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
18
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23
+ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ * POSSIBILITY OF SUCH DAMAGE.
25
+ */
26
+
27
+#ifndef _COMMON_H_
28
+#define _COMMON_H_
29
+
30
+#define MAX_BUF 16384
31
+ 
32
+#endif /* _COMMON_H_ */

+ 30
- 174
server.c View File

@@ -41,7 +41,6 @@
41 41
 #include <unistd.h>
42 42
 #include <errno.h>
43 43
 #include <err.h>
44
-#include <sys/queue.h>
45 44
 #include <sys/stat.h>
46 45
 
47 46
 /* Libevent. */
@@ -54,30 +53,9 @@
54 53
 /* LevelDB */
55 54
 #include <leveldb/c.h>
56 55
 
57
-#define SERVER_PORT 8080
58
-#define MAX_BUF 16384
59
-
60
-/**
61
- * A struct for client specific data, also includes pointer to create
62
- * a list of clients.
63
- */
64
-struct client {
65
-	/* The clients socket. */
66
-	int fd;
67
-
68
-	/* The bufferedevent for this client. */
69
-	struct bufferevent *buf_ev;
70
-
71
-	TAILQ_ENTRY(client) entries;
72
-};
73
-TAILQ_HEAD(, client) clients;
74
-
75
-struct queue {
76
-	char *queuename;
77
-	TAILQ_HEAD(, client) subscribers;
78
-	TAILQ_ENTRY(queue) entries;
79
-};
80
-TAILQ_HEAD(, queue) queues;
56
+#include "common.h"
57
+#include "server.h"
58
+#include "client.h"
81 59
 
82 60
 struct event_base *base;
83 61
 
@@ -119,64 +97,6 @@ int setnonblock(int fd)
119 97
 	return 0;
120 98
 }
121 99
 
122
-int find_readers(char *queuename, struct evbuffer *evb)
123
-{
124
-	struct queue *entry, *tmp_entry;
125
-	char buf[MAX_BUF];
126
-
127
-	*buf = '\0';
128
-	for (entry = TAILQ_FIRST(&queues); entry != NULL; entry = tmp_entry) {
129
-		tmp_entry = TAILQ_NEXT(entry, entries);
130
-		if (strncmp(queuename, entry->queuename, strlen(entry->queuename)) == 0){
131
-			evbuffer_add_printf(evb, "queue: %s", queuename);
132
-			//TAILQ_REMOVE(&readers, entry, entries);
133
-			return 1;
134
-		}
135
-	}
136
-	return 0;
137
-}
138
-
139
-int stomp_parse_headers(struct evkeyvalq* headers, struct evbuffer* buffer)
140
-{
141
-	char *line;
142
-	size_t line_length;
143
-	char *skey, *svalue;
144
-
145
-	TAILQ_INIT(headers);
146
-
147
-	while ((line = evbuffer_readln(buffer, &line_length, EVBUFFER_EOL_CRLF)) != NULL) {
148
-		skey = NULL;
149
-		svalue = NULL;
150
-
151
-		if (*line == '\0') {
152
-			free(line);
153
-			return 0;
154
-		}
155
-
156
-		/* Processing of header lines */
157
-		svalue = line;
158
-		skey = strsep(&svalue, ":");
159
-		if (svalue == NULL){
160
-			free(line);
161
-			return 1;
162
-		}
163
-
164
-		svalue += strspn(svalue, " ");
165
-
166
-		printf("HEADER: <%s> <%s>\n", skey, svalue);
167
-
168
-		if (evhttp_add_header(headers, skey, svalue) == -1){
169
-			free(line);
170
-			return 2;
171
-		}
172
-
173
-		free(line);
174
-	}
175
-
176
-	return 0;
177
-}
178
-
179
-
180 100
 /**
181 101
  * Called by libevent when there is data to read.
182 102
  */
@@ -185,80 +105,45 @@ void buffered_on_read(struct bufferevent *bev, void *arg)
185 105
 	/* Write back the read buffer. It is important to note that
186 106
 	 * bufferevent_write_buffer will drain the incoming data so it
187 107
 	 * is effectively gone after we call it. */
188
-	struct client *cli = (struct client *)arg;
189
-	struct queue *entry, *tmp_entry;
190
-	struct evbuffer *evb, *evb2;
191
-	char *request, *header_begin;
192
-	struct evkeyvalq *headers;
193
-	const char *queuename;
108
+	struct client *client = (struct client *)arg;
109
+	struct evbuffer *evb;
110
+	char *header_begin;
194 111
 	
195
-	request = evbuffer_readln(bufferevent_get_input(bev), NULL, EVBUFFER_EOL_NUL);
196
-	if (request == NULL) {
112
+	client->request = evbuffer_readln(bufferevent_get_input(bev), NULL, EVBUFFER_EOL_NUL);
113
+	if (client->request == NULL) {
197 114
 		return;
198 115
 	}
199
-	
200
-	header_begin = strstr(request, "\r\n");
116
+
117
+	header_begin = strstr(client->request, "\r\n");
201 118
 	if(header_begin == NULL){
202
-		free(request);
119
+		free(client->request);
203 120
 		return;
204 121
 	}
205 122
 
123
+	client->buf_out = evbuffer_new();
206 124
 	evb = evbuffer_new();
207
-	evb2 = evbuffer_new();
208 125
 
209
-	evbuffer_prepend(evb2, header_begin+2, strlen(header_begin+2));
126
+	evbuffer_prepend(evb, header_begin+2, strlen(header_begin+2));
210 127
 
211
-	headers = calloc(1, sizeof(struct evkeyvalq));
212
-	if(headers == NULL){
213
-		goto error;
128
+	if(stomp_parse_headers(client->headers, evb) != 0){
129
+		evbuffer_add_printf(client->buf_out, "Invalid Request\n");
214 130
 	}
215
-
216
-	if(stomp_parse_headers(headers, evb2) != 0){
217
-		evbuffer_add_printf(evb, "Invalid Request\n");
218
-	}
219
-	else if (strncmp(request, "SUBSCRIBE", 9) == 0) {
220
-		queuename = evhttp_find_header(headers, "destination");
221
-		if(queuename == NULL){
222
-			evbuffer_add_printf(evb, "Destination header missing\n");
223
-			goto error;
224
-		}
225
-
226
-		for (entry = TAILQ_FIRST(&queues); entry != NULL; entry = tmp_entry) {
227
-			tmp_entry = TAILQ_NEXT(entry, entries);
228
-			if (strcmp(entry->queuename, queuename) == 0){
229
-				evbuffer_add_printf(evb, "queue %s found\n", queuename);
230
-				entry = tmp_entry;
231
-				break;
232
-			}
233
-		}
234
-
235
-		if (entry == NULL){
236
-			entry = malloc(sizeof(*entry));
237
-			entry->queuename = malloc(strlen(queuename)+1);
238
-			strcpy(entry->queuename, queuename);
239
-			TAILQ_INIT(&entry->subscribers);
240
-			TAILQ_INSERT_TAIL(&queues, entry, entries);
241
-			evbuffer_add_printf(evb, "queue %s created\n", queuename);
242
-		}
243
-
244
-		/* TODO: check if already subscribed */
245
-
246
-		TAILQ_INSERT_TAIL(&entry->subscribers, cli, entries);
247
-	}
248
-	else if (strncmp(request, "exit", 4) == 0 || strncmp(request, "quit", 4) == 0) {
249
-		evbuffer_add_printf(evb, "ok bye\n");
250
-		shutdown(cli->fd, SHUT_RDWR);
131
+	else if (strncmp(client->request, "SUBSCRIBE", 9) == 0) {
132
+		/* TODO: improve interface API for handlers */
133
+        }
134
+	else if (strncmp(client->request, "exit", 4) == 0 || strncmp(client->request, "quit", 4) == 0) {
135
+		evbuffer_add_printf(client->buf_out, "ok bye\n");
136
+		shutdown(client->fd, SHUT_RDWR);
251 137
 	}
252 138
 	else {
253
-		evbuffer_add_printf(evb, "error unknown command\n");
139
+		evbuffer_add_printf(client->buf_out, "error unknown command\n");
254 140
 	}
255 141
 
256
-error:
257
-	bufferevent_write_buffer(bev, evb);
258
-	evbuffer_free(evb2);
142
+	bufferevent_write_buffer(bev, client->buf_out);
259 143
 	evbuffer_free(evb);
260
-	free(request);
261
-	free(headers);
144
+	evbuffer_free(client->buf_out);
145
+	free(client->request);
146
+	free(client->headers);
262 147
 }
263 148
 
264 149
 /**
@@ -297,7 +182,7 @@ void buffered_on_error(struct bufferevent *bev, short what, void *arg)
297 182
 
298 183
 	/* TODO: remove from subscribers */
299 184
 
300
-	bufferevent_free(client->buf_ev);
185
+	bufferevent_free(client->buf_in);
301 186
 	close(client->fd);
302 187
 	free(client);
303 188
 }
@@ -328,42 +213,13 @@ void on_accept(int fd, short ev, void *arg)
328 213
 	if (client == NULL)
329 214
 		err(1, "malloc failed");
330 215
 	client->fd = client_fd;
331
-	
332
-	/* Create the buffered event.
333
-	 *
334
-	 * The first argument is the file descriptor that will trigger
335
-	 * the events, in this case the clients socket.
336
-	 *
337
-	 * The second argument is the callback that will be called
338
-	 * when data has been read from the socket and is available to
339
-	 * the application.
340
-	 *
341
-	 * The third argument is a callback to a function that will be
342
-	 * called when the write buffer has reached a low watermark.
343
-	 * That usually means that when the write buffer is 0 length,
344
-	 * this callback will be called.  It must be defined, but you
345
-	 * don't actually have to do anything in this callback.
346
-	 *
347
-	 * The fourth argument is a callback that will be called when
348
-	 * there is a socket error.  This is where you will detect
349
-	 * that the client disconnected or other socket errors.
350
-	 *
351
-	 * The fifth and final argument is to store an argument in
352
-	 * that will be passed to the callbacks.  We store the client
353
-	 * object here.
354
-	 */
355
-	/*
356
-	client->buf_ev = bufferevent_new(client_fd, buffered_on_read,
357
-	    buffered_on_write, buffered_on_error, client);
358
-	*/
359
-
360
-	client->buf_ev = bufferevent_socket_new(base, client_fd, 0); 
361
-	bufferevent_setcb(client->buf_ev, buffered_on_read, buffered_on_write,
216
+	client->buf_in = bufferevent_socket_new(base, client_fd, 0); 
217
+	bufferevent_setcb(client->buf_in, buffered_on_read, buffered_on_write,
362 218
 		buffered_on_error, client);
363 219
 
364 220
 	/* We have to enable it before our callbacks will be
365 221
 	 * called. */
366
-	bufferevent_enable(client->buf_ev, EV_READ);
222
+	bufferevent_enable(client->buf_in, EV_READ);
367 223
 }
368 224
 
369 225
 int main(int argc, char **argv)

+ 37
- 0
server.h View File

@@ -0,0 +1,37 @@
1
+/*
2
+ * Copyright (C) 2011 Bernhard Froehlich <decke@bluelife.at>
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ *
9
+ * 1. Redistributions of source code must retain the above copyright
10
+ *    notice, this list of conditions and the following disclaimer.
11
+ * 2. Author's name may not be used endorse or promote products derived
12
+ *    from this software without specific prior written permission.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
18
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23
+ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ * POSSIBILITY OF SUCH DAMAGE.
25
+ */
26
+
27
+#ifndef _SERVER_H_
28
+#define _SERVER_H_
29
+
30
+#define REDQUEUE_VERSION "0.0.1"
31
+#define DAEMON_NAME "redqd"
32
+#define CONF_FILE "redqd.conf"
33
+#define PID_FILE "/var/run/redqd.pid"
34
+
35
+#define SERVER_PORT 8080
36
+ 
37
+#endif /* _SERVER_H_ */

+ 118
- 0
stomp.c View File

@@ -0,0 +1,118 @@
1
+/*
2
+ * Copyright (C) 2011 Bernhard Froehlich <decke@bluelife.at>
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ *
9
+ * 1. Redistributions of source code must retain the above copyright
10
+ *    notice, this list of conditions and the following disclaimer.
11
+ * 2. Author's name may not be used endorse or promote products derived
12
+ *    from this software without specific prior written permission.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
18
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23
+ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
+ * POSSIBILITY OF SUCH DAMAGE.
25
+ */
26
+
27
+#include <stdlib.h>
28
+#include <string.h>
29
+#include <sys/queue.h>
30
+
31
+#include <event2/buffer.h>
32
+#include <event2/bufferevent.h>
33
+#include <event2/http.h>
34
+#include <event2/keyvalq_struct.h>
35
+
36
+#include "client.h"
37
+
38
+
39
+int stomp_subscribe(struct client *client)
40
+{
41
+   struct queue *entry, *tmp_entry;
42
+   const char *queuename;
43
+
44
+   queuename = evhttp_find_header(client->headers, "destination");
45
+   if(queuename == NULL){
46
+      evbuffer_add_printf(client->buf_out, "Destination header missing\n");
47
+      return 1;
48
+   }
49
+         
50
+   for (entry = TAILQ_FIRST(&queues); entry != NULL; entry = tmp_entry) {
51
+      tmp_entry = TAILQ_NEXT(entry, entries);
52
+      if (strcmp(entry->queuename, queuename) == 0){
53
+         evbuffer_add_printf(client->buf_out, "queue %s found\n", queuename);
54
+         entry = tmp_entry;
55
+         break;
56
+      }
57
+   }
58
+
59
+   if (entry == NULL){
60
+      entry = malloc(sizeof(*entry));
61
+      entry->queuename = malloc(strlen(queuename)+1);
62
+      strcpy(entry->queuename, queuename);
63
+      TAILQ_INIT(&entry->subscribers);
64
+      TAILQ_INSERT_TAIL(&queues, entry, entries);
65
+      evbuffer_add_printf(client->buf_out, "queue %s created\n", queuename);
66
+   }
67
+
68
+   /* TODO: check if already subscribed */
69
+
70
+   TAILQ_INSERT_TAIL(&entry->subscribers, client, entries);
71
+
72
+   return 0;
73
+}
74
+
75
+
76
+int stomp_parse_headers(struct evkeyvalq* headers, struct evbuffer* buffer)
77
+{
78
+   char *line;
79
+   size_t line_length;
80
+   char *skey, *svalue;
81
+
82
+   headers = calloc(1, sizeof(struct evkeyvalq));
83
+   if(headers == NULL){
84
+      return 1;
85
+   }
86
+
87
+   TAILQ_INIT(headers);
88
+
89
+   while ((line = evbuffer_readln(buffer, &line_length, EVBUFFER_EOL_CRLF)) != NULL) {
90
+      skey = NULL;
91
+      svalue = NULL;
92
+
93
+      if (*line == '\0') {
94
+         free(line);
95
+         return 0;
96
+      }
97
+
98
+      /* Processing of header lines */
99
+      svalue = line;
100
+      skey = strsep(&svalue, ":");
101
+      if (svalue == NULL){
102
+         free(line);
103
+         return 2;
104
+      }
105
+
106
+      svalue += strspn(svalue, " ");
107
+
108
+      if (evhttp_add_header(headers, skey, svalue) == -1){
109
+         free(line);
110
+         return 1;
111
+      }
112
+
113
+      free(line);
114
+   }
115
+
116
+   return 0;
117
+}
118
+

Loading…
Cancel
Save