support for multiple routers

This commit is contained in:
Unbit
2013-09-14 15:07:43 +02:00
parent 5642aa1eb5
commit dbe15195b7
3 changed files with 145 additions and 130 deletions
+50 -50
View File
@@ -3,7 +3,7 @@
extern struct uwsgi_tuntap utt;
// create a new peer
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_create(int fd) {
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_create(struct uwsgi_tuntap_router *uttr, int fd) {
struct uwsgi_tuntap_peer *uttp = uwsgi_calloc(sizeof(struct uwsgi_tuntap_peer));
uttp->fd = fd;
@@ -11,21 +11,21 @@ struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_create(int fd) {
uttp->buf = uwsgi_malloc(utt.buffer_size + 4);
uttp->write_buf = uwsgi_malloc(utt.buffer_size);
if (utt.peers_tail) {
utt.peers_tail->next = uttp;
uttp->prev = utt.peers_tail;
utt.peers_tail = uttp;
if (uttr->peers_tail) {
uttr->peers_tail->next = uttp;
uttp->prev = uttr->peers_tail;
uttr->peers_tail = uttp;
}
else {
utt.peers_head = uttp;
utt.peers_tail = uttp;
uttr->peers_head = uttp;
uttr->peers_tail = uttp;
}
return uttp;
}
// destroy a peer
void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_peer *uttp) {
void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_router *uttr, struct uwsgi_tuntap_peer *uttp) {
struct uwsgi_tuntap_peer *prev = uttp->prev;
struct uwsgi_tuntap_peer *next = uttp->next;
@@ -37,12 +37,12 @@ void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_peer *uttp) {
next->prev = prev;
}
if (uttp == utt.peers_head) {
utt.peers_head = next;
if (uttp == uttr->peers_head) {
uttr->peers_head = next;
}
if (uttp == utt.peers_tail) {
utt.peers_tail = prev;
if (uttp == uttr->peers_tail) {
uttr->peers_tail = prev;
}
free(uttp->buf);
@@ -53,8 +53,8 @@ void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_peer *uttp) {
// get a peer by addr
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_get_by_addr(uint32_t addr) {
struct uwsgi_tuntap_peer *uttp = utt.peers_head;
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_get_by_addr(struct uwsgi_tuntap_router *uttr, uint32_t addr) {
struct uwsgi_tuntap_peer *uttp = uttr->peers_head;
while (uttp) {
if (uttp->addr == addr)
return uttp;
@@ -65,23 +65,23 @@ struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_get_by_addr(uint32_t addr) {
}
// block all reading peers
void uwsgi_tuntap_block_reads() {
struct uwsgi_tuntap_peer *uttp = utt.peers_head;
void uwsgi_tuntap_block_reads(struct uwsgi_tuntap_router *uttr) {
struct uwsgi_tuntap_peer *uttp = uttr->peers_head;
while (uttp) {
if (!uttp->blocked_read) {
if (!uttp->wait_for_write) {
if (event_queue_del_fd(utt.queue, uttp->fd, event_queue_read())) {
if (event_queue_del_fd(uttr->queue, uttp->fd, event_queue_read())) {
struct uwsgi_tuntap_peer *tmp_uttp = uttp;
uttp = uttp->next;
uwsgi_tuntap_peer_destroy(tmp_uttp);
uwsgi_tuntap_peer_destroy(uttr, tmp_uttp);
continue;
}
}
else {
if (event_queue_fd_readwrite_to_write(utt.queue, uttp->fd)) {
if (event_queue_fd_readwrite_to_write(uttr->queue, uttp->fd)) {
struct uwsgi_tuntap_peer *tmp_uttp = uttp;
uttp = uttp->next;
uwsgi_tuntap_peer_destroy(tmp_uttp);
uwsgi_tuntap_peer_destroy(uttr, tmp_uttp);
continue;
}
}
@@ -92,23 +92,23 @@ void uwsgi_tuntap_block_reads() {
}
//unblock all reading peers
void uwsgi_tuntap_unblock_reads() {
struct uwsgi_tuntap_peer *uttp = utt.peers_head;
void uwsgi_tuntap_unblock_reads(struct uwsgi_tuntap_router *uttr) {
struct uwsgi_tuntap_peer *uttp = uttr->peers_head;
while (uttp) {
if (uttp->blocked_read) {
if (!uttp->wait_for_write) {
if (event_queue_add_fd_read(utt.queue, uttp->fd)) {
if (event_queue_add_fd_read(uttr->queue, uttp->fd)) {
struct uwsgi_tuntap_peer *tmp_uttp = uttp;
uttp = uttp->next;
uwsgi_tuntap_peer_destroy(tmp_uttp);
uwsgi_tuntap_peer_destroy(uttr, tmp_uttp);
continue;
}
}
else {
if (event_queue_fd_write_to_readwrite(utt.queue, uttp->fd)) {
if (event_queue_fd_write_to_readwrite(uttr->queue, uttp->fd)) {
struct uwsgi_tuntap_peer *tmp_uttp = uttp;
uttp = uttp->next;
uwsgi_tuntap_peer_destroy(tmp_uttp);
uwsgi_tuntap_peer_destroy(uttr, tmp_uttp);
continue;
}
}
@@ -119,8 +119,8 @@ void uwsgi_tuntap_unblock_reads() {
}
// enqueue a packet in the tuntap device
void uwsgi_tuntap_enqueue() {
ssize_t rlen = write(utt.fd, utt.write_buf + utt.write_pos, utt.write_pktsize - utt.write_pos);
void uwsgi_tuntap_enqueue(struct uwsgi_tuntap_router *uttr) {
ssize_t rlen = write(uttr->fd, uttr->write_buf + uttr->write_pos, uttr->write_pktsize - uttr->write_pos);
// error on the tuntap device, destroy !!!
if (rlen == 0) {
uwsgi_error("uwsgi_tuntap_enqueue()/write()");
@@ -134,33 +134,33 @@ void uwsgi_tuntap_enqueue() {
exit(1);
}
utt.write_pos += rlen;
if (utt.write_pos >= utt.write_pktsize) {
utt.write_pos = 0;
if (utt.wait_for_write) {
if (event_queue_fd_write_to_read(utt.queue, utt.fd)) {
uttr->write_pos += rlen;
if (uttr->write_pos >= uttr->write_pktsize) {
uttr->write_pos = 0;
if (uttr->wait_for_write) {
if (event_queue_fd_write_to_read(uttr->queue, uttr->fd)) {
uwsgi_error("uwsgi_tuntap_enqueue()/event_queue_fd_read_to_write()");
exit(1);
}
utt.wait_for_write = 0;
uttr->wait_for_write = 0;
}
uwsgi_tuntap_unblock_reads();
uwsgi_tuntap_unblock_reads(uttr);
return;
}
retry:
if (!utt.wait_for_write) {
uwsgi_tuntap_block_reads();
if (event_queue_fd_read_to_write(utt.queue, utt.fd)) {
if (!uttr->wait_for_write) {
uwsgi_tuntap_block_reads(uttr);
if (event_queue_fd_read_to_write(uttr->queue, uttr->fd)) {
uwsgi_error("uwsgi_tuntap_enqueue()/event_queue_fd_read_to_write()");
exit(1);
}
utt.wait_for_write = 1;
uttr->wait_for_write = 1;
}
}
// receive a packet from the client
int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_peer *uttp) {
int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_router *uttr, struct uwsgi_tuntap_peer *uttp) {
// get body
if (uttp->header_pos >= 4) {
ssize_t rlen = read(uttp->fd, uttp->buf + uttp->buf_pos, uttp->buf_pktsize - uttp->buf_pos);
@@ -190,7 +190,7 @@ int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_peer *uttp) {
if (!uttp->addr)
return -1;
struct uwsgi_tuntap_peer *tmp_uttp = uwsgi_tuntap_peer_get_by_addr(uttp->addr);
struct uwsgi_tuntap_peer *tmp_uttp = uwsgi_tuntap_peer_get_by_addr(uttr, uttp->addr);
char ip[INET_ADDRSTRLEN + 1];
memset(ip, 0, INET_ADDRSTRLEN + 1);
if (!inet_ntop(AF_INET, &uttp->addr, ip, INET_ADDRSTRLEN)) {
@@ -199,14 +199,14 @@ int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_peer *uttp) {
}
if (uttp != tmp_uttp) {
uwsgi_log("[tuntap-router] detected ip collision for %s\n", ip);
uwsgi_tuntap_peer_destroy(tmp_uttp);
uwsgi_tuntap_peer_destroy(uttr, tmp_uttp);
}
uwsgi_log("[tuntap-router] registered new peer %s (fd: %d)\n", ip, uttp->fd);
}
memcpy(utt.write_buf, uttp->buf, uttp->buf_pktsize);
utt.write_pktsize = uttp->buf_pktsize;
uwsgi_tuntap_enqueue();
memcpy(uttr->write_buf, uttp->buf, uttp->buf_pktsize);
uttr->write_pktsize = uttp->buf_pktsize;
uwsgi_tuntap_enqueue(uttr);
}
return 0;
}
@@ -229,7 +229,7 @@ int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_peer *uttp) {
}
// enqueue a packet to the client
int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_peer *uttp) {
int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_router *uttr, struct uwsgi_tuntap_peer *uttp) {
ssize_t rlen = write(uttp->fd, uttp->write_buf + uttp->written, uttp->write_buf_pktsize - uttp->written);
if (rlen == 0) {
@@ -251,15 +251,15 @@ int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_peer *uttp) {
uttp->write_buf_pktsize = 0;
if (uttp->wait_for_write) {
// if the write ends while we are writing to the tuntap, block the reads
if (utt.wait_for_write) {
if (uttr->wait_for_write) {
uttp->blocked_read = 1;
if (event_queue_del_fd(utt.queue, uttp->fd, event_queue_write())) {
if (event_queue_del_fd(uttr->queue, uttp->fd, event_queue_write())) {
uwsgi_error("uwsgi_tuntap_peer_enqueue()/event_queue_del_fd()");
return -1;
}
}
else {
if (event_queue_fd_readwrite_to_read(utt.queue, uttp->fd)) {
if (event_queue_fd_readwrite_to_read(uttr->queue, uttp->fd)) {
uwsgi_error("uwsgi_tuntap_peer_enqueue()/event_queue_fd_write_to_read()");
return -1;
}
@@ -274,7 +274,7 @@ int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_peer *uttp) {
retry:
if (!uttp->wait_for_write) {
if (event_queue_fd_read_to_readwrite(utt.queue, uttp->fd)) {
if (event_queue_fd_read_to_readwrite(uttr->queue, uttp->fd)) {
uwsgi_error("uwsgi_tuntap_peer_enqueue()/event_queue_fd_read_to_write()");
return -1;
}
+17 -14
View File
@@ -43,33 +43,36 @@ struct uwsgi_tuntap_firewall_rule {
struct uwsgi_tuntap_firewall_rule *next;
};
struct uwsgi_tuntap {
char *addr;
char *device;
int fd;
struct uwsgi_tuntap_router {
int fd;
int server_fd;
int queue;
uint16_t buffer_size;
char *buf;
char *buf;
char *write_buf;
struct uwsgi_tuntap_peer *peers_head;
struct uwsgi_tuntap_peer *peers_tail;
uint16_t write_pktsize;
uint16_t write_pos;
int wait_for_write;
struct uwsgi_tuntap_peer *peers_head;
struct uwsgi_tuntap_peer *peers_tail;
};
struct uwsgi_tuntap {
struct uwsgi_string_list *routers;
struct uwsgi_string_list *devices;
uint16_t buffer_size;
struct uwsgi_tuntap_firewall_rule *fw_in;
struct uwsgi_tuntap_firewall_rule *fw_out;
};
int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_peer *);
int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_peer *);
void uwsgi_tuntap_enqueue();
int uwsgi_tuntap_peer_dequeue(struct uwsgi_tuntap_router *, struct uwsgi_tuntap_peer *);
int uwsgi_tuntap_peer_enqueue(struct uwsgi_tuntap_router *, struct uwsgi_tuntap_peer *);
void uwsgi_tuntap_enqueue(struct uwsgi_tuntap_router *);
int uwsgi_tuntap_firewall_check(struct uwsgi_tuntap_firewall_rule *, char *, uint16_t);
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_create(int);
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_get_by_addr(uint32_t);
void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_peer *);
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_create(struct uwsgi_tuntap_router *, int);
struct uwsgi_tuntap_peer *uwsgi_tuntap_peer_get_by_addr(struct uwsgi_tuntap_router *,uint32_t);
void uwsgi_tuntap_peer_destroy(struct uwsgi_tuntap_router *, struct uwsgi_tuntap_peer *);
int uwsgi_tuntap_device(char *);
+78 -66
View File
@@ -58,8 +58,8 @@ struct uwsgi_tuntap utt;
*/
static struct uwsgi_option uwsgi_tuntap_options[] = {
{"tuntap-router", required_argument, 0, "run the tuntap router (syntax: <device> <socket>)", uwsgi_opt_set_str, &utt.addr, 0},
{"tuntap-device", required_argument, 0, "add a tuntap device to the instance (syntax: <device>[ <socket>])", uwsgi_opt_set_str, &utt.device, 0},
{"tuntap-router", required_argument, 0, "run the tuntap router (syntax: <device> <socket>)", uwsgi_opt_add_string_list, &utt.routers, 0},
{"tuntap-device", required_argument, 0, "add a tuntap device to the instance (syntax: <device>[ <socket>])", uwsgi_opt_add_string_list, &utt.devices, 0},
{"tuntap-router-firewall-in", required_argument, 0, "add a firewall rule to the tuntap router (syntax: <action> <src/mask> <dst/mask>)", uwsgi_tuntap_opt_firewall, &utt.fw_in, 0},
{"tuntap-router-firewall-out", required_argument, 0, "add a firewall rule to the tuntap router (syntax: <action> <src/mask> <dst/mask>)", uwsgi_tuntap_opt_firewall, &utt.fw_out, 0},
{NULL, 0, 0, NULL, NULL, NULL, 0},
@@ -75,57 +75,57 @@ static void *uwsgi_tuntap_loop(void *arg) {
#endif
pthread_sigmask(SIG_BLOCK, &smask, NULL);
int fd = utt.fd;
struct uwsgi_tuntap_router *uttr = (struct uwsgi_tuntap_router *) arg;
uwsgi_socket_nb(fd);
uwsgi_socket_nb(uttr->fd);
if (!utt.buffer_size)
utt.buffer_size = 8192;
utt.buf = uwsgi_malloc(utt.buffer_size);
utt.write_buf = uwsgi_malloc(utt.buffer_size);
uttr->buf = uwsgi_malloc(utt.buffer_size);
uttr->write_buf = uwsgi_malloc(utt.buffer_size);
utt.queue = event_queue_init();
uttr->queue = event_queue_init();
event_queue_add_fd_read(utt.queue, fd);
event_queue_add_fd_read(uttr->queue, uttr->fd);
int server_fd = uwsgi_connect("/tmp/tuntap.socket", 30, 0);
if (server_fd < 0) {
uwsgi_error("uwsgi_tuntap_loop()/uwsgi_connect()");
exit(1);
}
if (event_queue_add_fd_read(utt.queue, server_fd)) {
if (event_queue_add_fd_read(uttr->queue, server_fd)) {
exit(1);
}
uwsgi_socket_nb(server_fd);
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_create(server_fd);
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_create(uttr, server_fd);
for (;;) {
int interesting_fd = -1;
int ret = event_queue_wait(utt.queue, -1, &interesting_fd);
int ret = event_queue_wait(uttr->queue, -1, &interesting_fd);
if (ret <= 0)
continue;
if (interesting_fd == fd) {
if (utt.wait_for_write) {
uwsgi_tuntap_enqueue();
if (interesting_fd == uttr->fd) {
if (uttr->wait_for_write) {
uwsgi_tuntap_enqueue(uttr);
continue;
}
ssize_t rlen = read(fd, utt.buf, utt.buffer_size);
ssize_t rlen = read(uttr->fd, uttr->buf, utt.buffer_size);
if (rlen <= 0) {
uwsgi_error("uwsgi_tuntap_loop()/read()");
exit(1);
}
uint16_t pktsize = rlen;
char *ptr = uttp->write_buf + uttp->write_buf_pktsize;
memcpy(ptr + 4, utt.buf, rlen);
memcpy(ptr + 4, uttr->buf, rlen);
ptr[0] = 0;
ptr[1] = (uint8_t) (pktsize & 0xff);
ptr[2] = (uint8_t) ((pktsize >> 8) & 0xff);
ptr[3] = 0;
uttp->write_buf_pktsize+= pktsize+4;
if (uwsgi_tuntap_peer_enqueue(uttp)) {
if (uwsgi_tuntap_peer_enqueue(uttr, uttp)) {
uwsgi_log("server disconnected...\n");
exit(1);
}
@@ -136,19 +136,19 @@ static void *uwsgi_tuntap_loop(void *arg) {
if (interesting_fd == server_fd) {
// read from the client
if (!uttp->wait_for_write) {
if (uwsgi_tuntap_peer_dequeue(uttp)) {
if (uwsgi_tuntap_peer_dequeue(uttr, uttp)) {
uwsgi_log("server disconnected...\n");
exit(1);
}
}
else {
// something is wrong (the tuntap device is blocked)
if (utt.wait_for_write) {
if (uttr->wait_for_write) {
continue;
}
// write to the client
if (uwsgi_tuntap_peer_enqueue(uttp)) {
if (uwsgi_tuntap_peer_enqueue(uttr, uttp)) {
uwsgi_log("server disconnected...\n");
exit(1);
}
@@ -161,45 +161,52 @@ static void *uwsgi_tuntap_loop(void *arg) {
static void uwsgi_tuntap_client() {
if (!utt.device) return;
if (!utt.devices) return;
struct uwsgi_string_list *usl;
uwsgi_foreach(usl, utt.devices) {
struct uwsgi_tuntap_router *uttr = uwsgi_calloc(sizeof(struct uwsgi_tuntap_router));
uttr->fd = uwsgi_tuntap_device(usl->value);
utt.fd = uwsgi_tuntap_device(utt.device);
pthread_t t;
pthread_create(&t, NULL, uwsgi_tuntap_loop, NULL);
pthread_t t;
pthread_create(&t, NULL, uwsgi_tuntap_loop, uttr);
}
}
void uwsgi_tuntap_router_loop(int id, void *foobar) {
void uwsgi_tuntap_router_loop(int id, void *arg) {
int i;
utt.buf = uwsgi_malloc(utt.buffer_size);
utt.write_buf = uwsgi_malloc(utt.buffer_size);
utt.queue = event_queue_init();
struct uwsgi_tuntap_router *uttr = (struct uwsgi_tuntap_router *) arg;
uttr->buf = uwsgi_malloc(utt.buffer_size);
uttr->write_buf = uwsgi_malloc(utt.buffer_size);
uttr->queue = event_queue_init();
void *events = event_queue_alloc(64);
if (event_queue_add_fd_read(utt.queue, utt.server_fd))
if (event_queue_add_fd_read(uttr->queue, uttr->server_fd))
exit(1);
if (event_queue_add_fd_read(utt.queue, utt.fd))
if (event_queue_add_fd_read(uttr->queue, uttr->fd))
exit(1);
for (;;) {
int nevents = event_queue_wait_multi(utt.queue, -1, events, 64);
int nevents = event_queue_wait_multi(uttr->queue, -1, events, 64);
for (i = 0; i < nevents; i++) {
int interesting_fd = event_queue_interesting_fd(events, i);
if (interesting_fd == utt.fd) {
if (interesting_fd == uttr->fd) {
// if writing, continue enqueuing
if (utt.wait_for_write) {
uwsgi_tuntap_enqueue();
if (uttr->wait_for_write) {
uwsgi_tuntap_enqueue(uttr);
continue;
}
ssize_t rlen = read(utt.fd, utt.buf, utt.buffer_size);
ssize_t rlen = read(uttr->fd, uttr->buf, utt.buffer_size);
if (rlen <= 0) {
uwsgi_error("uwsgi_tuntap_router_loop()/read()");
exit(1);
}
if (uwsgi_tuntap_firewall_check(utt.fw_in, utt.buf, rlen)) continue;
if (uwsgi_tuntap_firewall_check(utt.fw_in, uttr->buf, rlen)) continue;
uint32_t *dst_ip = (uint32_t *) & utt.buf[16];
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_get_by_addr(*dst_ip);
uint32_t *dst_ip = (uint32_t *) & uttr->buf[16];
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_get_by_addr(uttr, *dst_ip);
if (!uttp)
continue;
@@ -211,50 +218,50 @@ void uwsgi_tuntap_router_loop(int id, void *foobar) {
uint16_t pktsize = rlen;
char *ptr = uttp->write_buf + uttp->write_buf_pktsize;
memcpy(ptr + 4, utt.buf, rlen);
memcpy(ptr + 4, uttr->buf, rlen);
ptr[0] = 0;
ptr[1] = (uint8_t) (pktsize & 0xff);
ptr[2] = (uint8_t) ((pktsize >> 8) & 0xff);
ptr[3] = 0;
uttp->write_buf_pktsize+= pktsize+4;
if (uwsgi_tuntap_peer_enqueue(uttp)) {
uwsgi_tuntap_peer_destroy(uttp);
if (uwsgi_tuntap_peer_enqueue(uttr, uttp)) {
uwsgi_tuntap_peer_destroy(uttr, uttp);
}
continue;
}
if (interesting_fd == utt.server_fd) {
int client_fd = uwsgi_accept(utt.server_fd);
if (interesting_fd == uttr->server_fd) {
int client_fd = uwsgi_accept(uttr->server_fd);
if (client_fd < 0) {
uwsgi_error("uwsgi_tuntap_server_loop()/accept()");
continue;
}
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_create(client_fd);
if (event_queue_add_fd_read(utt.queue, uttp->fd)) {
uwsgi_tuntap_peer_destroy(uttp);
struct uwsgi_tuntap_peer *uttp = uwsgi_tuntap_peer_create(uttr, client_fd);
if (event_queue_add_fd_read(uttr->queue, uttp->fd)) {
uwsgi_tuntap_peer_destroy(uttr, uttp);
}
continue;
}
struct uwsgi_tuntap_peer *uttp = utt.peers_head;
struct uwsgi_tuntap_peer *uttp = uttr->peers_head;
while (uttp) {
if (interesting_fd == uttp->fd) {
// read from the client
if (event_queue_interesting_fd_is_read(events, i)) {
if (uwsgi_tuntap_peer_dequeue(uttp)) {
uwsgi_tuntap_peer_destroy(uttp);
if (uwsgi_tuntap_peer_dequeue(uttr, uttp)) {
uwsgi_tuntap_peer_destroy(uttr, uttp);
break;
}
}
if (event_queue_interesting_fd_is_write(events, i)) {
// something is wrong (the tuntap device is blocked)
if (utt.wait_for_write)
if (uttr->wait_for_write)
break;
// write to the client
if (uwsgi_tuntap_peer_enqueue(uttp)) {
uwsgi_tuntap_peer_destroy(uttp);
if (uwsgi_tuntap_peer_enqueue(uttr, uttp)) {
uwsgi_tuntap_peer_destroy(uttr, uttp);
break;
}
}
@@ -268,26 +275,31 @@ void uwsgi_tuntap_router_loop(int id, void *foobar) {
static void uwsgi_tuntap_router() {
if (!utt.addr) return;
if (!utt.routers) return;
if (!utt.buffer_size)
utt.buffer_size = 8192;
char *space = strchr(utt.addr, ' ');
if (!space) {
uwsgi_log("invalid tuntap router syntax, must be <device> <socket>\n");
exit(1);
}
struct uwsgi_string_list *usl;
uwsgi_foreach(usl, utt.routers) {
char *space = strchr(usl->value, ' ');
if (!space) {
uwsgi_log("invalid tuntap router syntax, must be <device> <socket>\n");
exit(1);
}
utt.server_fd = bind_to_unix(space+1, uwsgi.listen_queue, uwsgi.chmod_socket, uwsgi.abstract_socket);
struct uwsgi_tuntap_router *uttr = uwsgi_calloc(sizeof(struct uwsgi_tuntap_router));
*space = 0 ;
utt.fd = uwsgi_tuntap_device(utt.addr);
*space = ' ';
uttr->server_fd = bind_to_unix(space+1, uwsgi.listen_queue, uwsgi.chmod_socket, uwsgi.abstract_socket);
if (register_gateway("uWSGI tuntap router", uwsgi_tuntap_router_loop, NULL) == NULL) {
uwsgi_log("unable to register the tuntap server gateway\n");
exit(1);
*space = 0 ;
uttr->fd = uwsgi_tuntap_device(usl->value);
*space = ' ';
if (register_gateway("uWSGI tuntap router", uwsgi_tuntap_router_loop, uttr) == NULL) {
uwsgi_log("unable to register the tuntap server gateway\n");
exit(1);
}
}
}