X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?a=blobdiff_plain;ds=sidebyside;f=tun.c;h=3db998f37fcd24d05b910d84111ea779fd9b4fbd;hb=cb14700acc2f7861981cc56c96d0fce2bdfe7fe9;hp=04ac08b8767ff668c46e8243ccf4153cfe5117e0;hpb=7c006408372213194fce572e390d8f474db9cebc;p=secnet.git diff --git a/tun.c b/tun.c index 04ac08b..3db998f 100644 --- a/tun.c +++ b/tun.c @@ -3,6 +3,7 @@ #include "netlink.h" #include #include +#include #include #include #include @@ -95,8 +96,7 @@ static cstring_t tun_flavour_str(uint32_t flavour) } static int tun_beforepoll(void *sst, struct pollfd *fds, int *nfds_io, - int *timeout_io, const struct timeval *tv_now, - uint64_t *now) + int *timeout_io) { struct tun *st=sst; *nfds_io=1; @@ -105,8 +105,7 @@ static int tun_beforepoll(void *sst, struct pollfd *fds, int *nfds_io, return 0; } -static void tun_afterpoll(void *sst, struct pollfd *fds, int nfds, - const struct timeval *tv_now, uint64_t *now) +static void tun_afterpoll(void *sst, struct pollfd *fds, int nfds) { struct tun *st=sst; int l; @@ -136,11 +135,27 @@ static void tun_afterpoll(void *sst, struct pollfd *fds, int nfds, static void tun_deliver_to_kernel(void *sst, struct buffer_if *buf) { struct tun *st=sst; + ssize_t rc; BUF_ASSERT_USED(buf); - /* No error checking, because we'd just throw the packet away - anyway if it didn't work. */ - write(st->fd,buf->start,buf->size); + + /* Log errors, so we can tell what's going on, but only once a + minute, so we don't flood the logs. Short writes count as + errors. */ + rc = write(st->fd,buf->start,buf->size); + if(rc != buf->size) { + static struct timeval last_report; + if(tv_now_global.tv_sec >= last_report.tv_sec + 60) { + if(rc < 0) + Message(M_WARNING, + "failed to deliver packet to tun device: %s\n", + strerror(errno)); + else + Message(M_WARNING, + "truncated packet delivered to tun device\n"); + last_report = tv_now_global; + } + } BUF_FREE(buf); } @@ -149,7 +164,7 @@ static bool_t tun_set_route(void *sst, struct netlink_client *routes) struct tun *st=sst; string_t network, mask, secnetaddr; struct subnet_list *nets; - uint32_t i; + int32_t i; int fd=-1; if (routes->up == routes->kup) return False; @@ -334,7 +349,7 @@ static void tun_phase_hook(void *sst, uint32_t newphase) hostaddr=ipaddr_to_string(st->local_address); secnetaddr=ipaddr_to_string(st->nl.secnet_address); - snprintf(mtu,6,"%d",st->nl.mtu); + snprintf(mtu,sizeof(mtu),"%d",st->nl.mtu); mtu[5]=0; switch (st->ifconfig_type) { @@ -481,10 +496,7 @@ static list_t *tun_create(closure_t *self, struct cloc loc, dict_t *context, fatal_perror("tun_create: uname"); } if (strcmp(u.sysname,"Linux")==0) { - if (u.release[0]=='2' && u.release[1]=='.' && u.release[3]=='.') { - if (u.release[2]=='2') st->tun_flavour=TUN_FLAVOUR_BSD; - else if (u.release[2]=='4') st->tun_flavour=TUN_FLAVOUR_LINUX; - } + st->tun_flavour=TUN_FLAVOUR_LINUX; } else if (strcmp(u.sysname,"SunOS")==0) { st->tun_flavour=TUN_FLAVOUR_STREAMS; } else if (strcmp(u.sysname,"FreeBSD")==0