summaryrefslogtreecommitdiffstats
path: root/src/multichannel.c
diff options
context:
space:
mode:
authorPablo Neira Ayuso <pablo@netfilter.org>2009-03-12 21:09:27 +0100
committerPablo Neira Ayuso <pablo@netfilter.org>2009-03-12 21:09:27 +0100
commit656d5ad7c69a5a7d356c6251743890f1eec0bb71 (patch)
tree46c7fe13a32382c556a51d258fab5b7bebe9cd77 /src/multichannel.c
parent56b484e3acc7205f0ebd71eec6905253eeace132 (diff)
sync-mode: add abstract layer to make daemon independent of multicast
This patch reworks conntrackd to make it independent of the protocol used to propagate state-changes. This patch adds the channel layer abstraction, this layer allows you to add support for different protocols like unicast UDP or TIPC. Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Diffstat (limited to 'src/multichannel.c')
-rw-r--r--src/multichannel.c110
1 files changed, 110 insertions, 0 deletions
diff --git a/src/multichannel.c b/src/multichannel.c
new file mode 100644
index 0000000..ab0f04c
--- /dev/null
+++ b/src/multichannel.c
@@ -0,0 +1,110 @@
+/*
+ * (C) 2009 by Pablo Neira Ayuso <pablo@netfilter.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#include <stdlib.h>
+
+#include "channel.h"
+#include "network.h"
+
+struct multichannel *
+multichannel_open(struct channel_conf *conf, int len)
+{
+ struct multichannel *m;
+ int i, set_default_channel = 0;
+
+ if (len <= 0 || len > MULTICHANNEL_MAX)
+ return NULL;
+
+ m = calloc(sizeof(struct multichannel), 1);
+ if (m == NULL)
+ return NULL;
+
+ m->channel_num = len;
+ for (i = 0; i < len; i++) {
+ m->channel[i] = channel_open(&conf[i]);
+ if (m->channel[i] == NULL) {
+ int j;
+
+ for (j=0; j<i; j++) {
+ channel_close(m->channel[j]);
+ }
+ free(m);
+ return NULL;
+ }
+ if (conf[i].channel_flags & CHANNEL_F_DEFAULT) {
+ m->current = m->channel[i];
+ set_default_channel = 1;
+ }
+ }
+ if (!set_default_channel)
+ m->current = m->channel[0];
+
+ return m;
+}
+
+int multichannel_send(struct multichannel *c, const struct nethdr *net)
+{
+ return channel_send(c->current, net);
+}
+
+int multichannel_send_flush(struct multichannel *c)
+{
+ return channel_send_flush(c->current);
+}
+
+int multichannel_recv(struct multichannel *c, char *buf, int size)
+{
+ return channel_recv(c->current, buf, size);
+}
+
+void multichannel_close(struct multichannel *m)
+{
+ int i;
+
+ for (i = 0; i < m->channel_num; i++) {
+ channel_close(m->channel[i]);
+ }
+ free(m);
+}
+
+void multichannel_stats(struct multichannel *m, int fd)
+{
+ channel_stats(m->current, fd);
+}
+
+void
+multichannel_stats_extended(struct multichannel *m,
+ struct nlif_handle *h, int fd)
+{
+ int i, active;
+
+ for (i = 0; i < m->channel_num; i++) {
+ if (m->current == m->channel[i]) {
+ active = 1;
+ } else {
+ active = 0;
+ }
+ channel_stats_extended(m->channel[i], active, h, fd);
+ }
+}
+
+int multichannel_get_ifindex(struct multichannel *m, int i)
+{
+ return m->channel[i]->channel_ifindex;
+}
+
+int multichannel_get_current_ifindex(struct multichannel *m)
+{
+ return m->current->channel_ifindex;
+}
+
+void multichannel_set_current_channel(struct multichannel *m, int i)
+{
+ m->current = m->channel[i];
+}