we don't need TAP

pull/18/head
Jeff Becker 6 years ago
parent 88da477f49
commit 685fc464c0
No known key found for this signature in database
GPG Key ID: F357B3B42F6F9B05

@ -40,9 +40,10 @@
#else
#include <net/if.h>
#endif
#include <netinet/if_ether.h>
#if defined Linux
#include <netinet/in.h>
#else
#include <netinet/if_ether.h>
#endif
#endif
@ -51,20 +52,6 @@
#ifndef LIBTUNTAP_H_
#define LIBTUNTAP_H_
/*
* Uniformize macros
* - ETHER_ADDR_LEN: Magic number from IEEE 802.3
* - IF_NAMESIZE: Length of interface external name
* - IF_DESCRSIZE: Length of interface description
* - TUNSDEBUG: ioctl flag to enable the debug mode of a tun device
* - TUNFD_INVALID_VALUE: Invalid value for tun_fd
*/
#if defined ETH_ALEN /* Linux */
#define ETHER_ADDR_LEN ETH_ALEN
#elif defined Windows || defined __sun__
#define ETHER_ADDR_LEN 6
#endif
#if defined IFNAMSIZ && !defined IF_NAMESIZE
#define IF_NAMESIZE IFNAMSIZ /* Historical BSD name */
#elif !defined IF_NAMESIZE
@ -151,7 +138,6 @@ extern "C"
t_tun tun_fd;
int ctrl_sock;
int flags; /* ifr.ifr_flags on Unix */
unsigned char hwaddr[ETHER_ADDR_LEN];
char if_name[IF_NAMESIZE];
#if defined(FreeBSD)
int mode;
@ -183,10 +169,7 @@ extern "C"
tuntap_get_ifname(struct device *);
TUNTAP_EXPORT int
tuntap_set_ifname(struct device *, const char *);
TUNTAP_EXPORT char *
tuntap_get_hwaddr(struct device *);
TUNTAP_EXPORT int
tuntap_set_hwaddr(struct device *, const char *);
TUNTAP_EXPORT int
tuntap_set_descr(struct device *, const char *);
TUNTAP_EXPORT int
@ -202,7 +185,8 @@ extern "C"
*/
TUNTAP_EXPORT int
tuntap_set_ip(struct device *, const char * srcaddr, const char *dstaddr, int netmask);
tuntap_set_ip(struct device *, const char *srcaddr, const char *dstaddr,
int netmask);
// TUNTAP_EXPORT int tuntap_set_ip_old(struct device *, const char
// *, int);
/*TUNTAP_EXPORT int tuntap_set_ip_old(struct device *, const char
@ -234,8 +218,6 @@ extern "C"
void
tuntap_sys_destroy(struct device *);
int
tuntap_sys_set_hwaddr(struct device *, struct ether_addr *);
int
tuntap_sys_set_ipv4(struct device *, t_tun_in_addr *, uint32_t);
#if defined(FreeBSD)

@ -48,55 +48,54 @@ static int
fucky_tuntap_sys_start(struct device *dev, int mode, int tun)
{
uint32_t namesz = IFNAMSIZ;
char name[IFNAMSIZ+1];
char name[IFNAMSIZ + 1];
int fd;
char *ifname;
fd = socket(PF_SYSTEM, SOCK_DGRAM, SYSPROTO_CONTROL);
if(fd == -1)
return fd;
snprintf(name, sizeof(name), "utun%i", tun);
struct ctl_info info;
memset(&info, 0, sizeof(info));
strncpy(info.ctl_name, APPLE_UTUN, strlen(APPLE_UTUN));
if (ioctl(fd, CTLIOCGINFO, &info) < 0)
if(ioctl(fd, CTLIOCGINFO, &info) < 0)
{
tuntap_log(TUNTAP_LOG_ERR, "call to ioctl() failed");
tuntap_log(TUNTAP_LOG_ERR, strerror(errno));
close(fd);
return -1;
}
struct sockaddr_ctl addr;
addr.sc_id = info.ctl_id;
addr.sc_len = sizeof(addr);
addr.sc_family = AF_SYSTEM;
addr.sc_len = sizeof(addr);
addr.sc_family = AF_SYSTEM;
addr.ss_sysaddr = AF_SYS_CONTROL;
addr.sc_unit = tun + 1;
addr.sc_unit = tun + 1;
if (connect(fd, (struct sockaddr*)&addr, sizeof(addr)) < 0)
if(connect(fd, (struct sockaddr *)&addr, sizeof(addr)) < 0)
{
close(fd);
return -1;
}
ifname = name;
if(getsockopt(fd, SYSPROTO_CONTROL, UTUN_OPT_IFNAME,
ifname, &namesz) < 0 )
if(getsockopt(fd, SYSPROTO_CONTROL, UTUN_OPT_IFNAME, ifname, &namesz) < 0)
{
close(fd);
return -1;
}
strncpy(dev->if_name, ifname, sizeof(dev->if_name));
return fd;
}
int tuntap_sys_start(struct device * dev, int mode, int tun)
int
tuntap_sys_start(struct device *dev, int mode, int tun)
{
int fd = -1;
while(tun < 128)
@ -116,25 +115,7 @@ int tuntap_sys_start(struct device * dev, int mode, int tun)
void
tuntap_sys_destroy(struct device *dev)
{
(void) dev;
}
int
tuntap_sys_set_hwaddr(struct device *dev, struct ether_addr *eth_addr)
{
struct ifreq ifr;
(void)memset(&ifr, '\0', sizeof ifr);
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof ifr.ifr_name);
ifr.ifr_addr.sa_len = ETHER_ADDR_LEN;
ifr.ifr_addr.sa_family = AF_LINK;
(void)memcpy(ifr.ifr_addr.sa_data, eth_addr, ETHER_ADDR_LEN);
if(ioctl(dev->ctrl_sock, SIOCSIFLLADDR, &ifr) < 0)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set link-layer address");
return -1;
}
return 0;
(void)dev;
}
struct tuntap_rtmsg
@ -149,33 +130,36 @@ int
tuntap_sys_set_ipv4(struct device *dev, t_tun_in_addr *s4, uint32_t bits)
{
struct sockaddr_in mask;
mask.sin_family = AF_INET;
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof(struct sockaddr_in);
mask.sin_len = sizeof(struct sockaddr_in);
char addrbuf[32];
inet_ntop(AF_INET, s4, addrbuf, sizeof(struct sockaddr_in));
char buf[1028];
const char * addr = addrbuf;
const char * netmask = inet_ntoa(mask.sin_addr);
const char *addr = addrbuf;
const char *netmask = inet_ntoa(mask.sin_addr);
/** because fuck this other stuff */
snprintf(buf, sizeof(buf), "ifconfig %s %s %s mtu 1380 netmask %s up", dev->if_name, addr, addr, netmask);
snprintf(buf, sizeof(buf), "ifconfig %s %s %s mtu 1380 netmask %s up",
dev->if_name, addr, addr, netmask);
tuntap_log(TUNTAP_LOG_INFO, buf);
system(buf);
snprintf(buf, sizeof(buf), "route add -cloning -net %s -netmask %s -interface %s", addr, netmask, dev->if_name);
snprintf(buf, sizeof(buf),
"route add -cloning -net %s -netmask %s -interface %s", addr,
netmask, dev->if_name);
tuntap_log(TUNTAP_LOG_INFO, buf);
system(buf);
/* Simpler than calling SIOCSIFADDR and/or SIOCSIFBRDADDR */
/*
if(ioctl(dev->ctrl_sock, SIOCSIFADDR, &ifa) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP");
tuntap_log(TUNTAP_LOG_ERR, strerror(errno));
return -1;
}
*/
/*
if(ioctl(dev->ctrl_sock, SIOCSIFADDR, &ifa) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP");
tuntap_log(TUNTAP_LOG_ERR, strerror(errno));
return -1;
}
*/
/*
int fd = socket(PF_ROUTE, SOCK_RAW, AF_INET);
struct tuntap_rtmsg msg;
@ -199,7 +183,7 @@ tuntap_sys_set_ipv4(struct device *dev, t_tun_in_addr *s4, uint32_t bits)
msg.mask.sin_addr.s_addr = bits;
msg.mask.sin_family = AF_INET;
msg.mask.sin_len = sizeof(struct sockaddr_in);
int res = write(fd, &msg, sizeof(msg));
if(res == -1)
{

@ -33,9 +33,9 @@
#include <arpa/inet.h>
#include <net/if.h>
#if defined FreeBSD
# include <net/if_tun.h>
#include <net/if_tun.h>
#elif defined DragonFly
# include <net/tun/if_tun.h>
#include <net/tun/if_tun.h>
#endif
#include <net/if_types.h>
#include <netinet/if_ether.h>
@ -53,234 +53,206 @@
#include "tuntap.h"
int
tuntap_sys_start(struct device *dev, int mode, int tun) {
int fd;
int persist;
char *ifname;
char name[MAXPATHLEN];
struct ifaddrs *ifa;
struct ifreq ifr;
/* Get the persistence bit */
if (mode & TUNTAP_MODE_PERSIST) {
mode &= ~TUNTAP_MODE_PERSIST;
persist = 1;
} else {
persist = 0;
}
/* Set the mode: tun or tap */
if (mode == TUNTAP_MODE_ETHERNET) {
ifname = "tap";
} else if (mode == TUNTAP_MODE_TUNNEL) {
ifname = "tun";
} else {
tuntap_log(TUNTAP_LOG_ERR, "Invalid parameter 'mode'");
return -1;
}
tuntap_sys_start(struct device *dev, int mode, int tun)
{
int fd;
int persist;
char *ifname;
char name[MAXPATHLEN];
struct ifaddrs *ifa;
struct ifreq ifr;
/* Get the persistence bit */
if(mode & TUNTAP_MODE_PERSIST)
{
mode &= ~TUNTAP_MODE_PERSIST;
persist = 1;
}
else
{
persist = 0;
}
/* Set the mode: tun or tap */
if(mode == TUNTAP_MODE_ETHERNET)
{
ifname = "tap";
}
else if(mode == TUNTAP_MODE_TUNNEL)
{
ifname = "tun";
}
else
{
tuntap_log(TUNTAP_LOG_ERR, "Invalid parameter 'mode'");
return -1;
}
dev->mode = mode;
/* Try to use the given driver or loop throught the avaible ones */
fd = -1;
if (tun < TUNTAP_ID_MAX) {
(void)snprintf(name, sizeof(name), "/dev/%s%i", ifname, tun);
fd = open(name, O_RDWR);
} else if (tun == TUNTAP_ID_ANY) {
for (tun = 0; tun < TUNTAP_ID_MAX; ++tun) {
(void)memset(name, 0, sizeof(name));
(void)snprintf(name, sizeof(name), "/dev/%s%i",
ifname, tun);
if ((fd = open(name, O_RDWR)) > 0)
break;
}
} else {
tuntap_log(TUNTAP_LOG_ERR, "Invalid parameter 'tun'");
return -1;
}
switch (fd) {
case -1:
tuntap_log(TUNTAP_LOG_ERR, "Permission denied");
return -1;
case 256:
tuntap_log(TUNTAP_LOG_ERR, "Can't find a tun entry");
return -1;
default:
/* NOTREACHED */
break;
}
/* Set the interface name */
(void)memset(&ifr, 0, sizeof(ifr));
(void)snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%i", ifname, tun);
/* And save it */
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof(dev->if_name));
/* Get the interface default values */
if (ioctl(dev->ctrl_sock, SIOCGIFFLAGS, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
/* Save pre-existing MAC address */
if (mode == TUNTAP_MODE_ETHERNET && getifaddrs(&ifa) == 0) {
struct ifaddrs *pifa;
for (pifa = ifa; pifa != NULL; pifa = pifa->ifa_next) {
if (strcmp(pifa->ifa_name, dev->if_name) == 0) {
struct ether_addr eth_addr;
/*
* The MAC address is from 10 to 15.
*
* And yes, I know, the buffer is supposed
* to have a size of 14 bytes.
*/
(void)memcpy(dev->hwaddr,
pifa->ifa_addr->sa_data + 10,
ETHER_ADDR_LEN);
(void)memset(&eth_addr.octet, 0,
ETHER_ADDR_LEN);
(void)memcpy(&eth_addr.octet,
pifa->ifa_addr->sa_data + 10,
ETHER_ADDR_LEN);
break;
}
}
if (pifa == NULL)
tuntap_log(TUNTAP_LOG_WARN,
"Can't get link-layer address");
freeifaddrs(ifa);
}
return fd;
/* Try to use the given driver or loop throught the avaible ones */
fd = -1;
if(tun < TUNTAP_ID_MAX)
{
(void)snprintf(name, sizeof(name), "/dev/%s%i", ifname, tun);
fd = open(name, O_RDWR);
}
else if(tun == TUNTAP_ID_ANY)
{
for(tun = 0; tun < TUNTAP_ID_MAX; ++tun)
{
(void)memset(name, 0, sizeof(name));
(void)snprintf(name, sizeof(name), "/dev/%s%i", ifname, tun);
if((fd = open(name, O_RDWR)) > 0)
break;
}
}
else
{
tuntap_log(TUNTAP_LOG_ERR, "Invalid parameter 'tun'");
return -1;
}
switch(fd)
{
case -1:
tuntap_log(TUNTAP_LOG_ERR, "Permission denied");
return -1;
case 256:
tuntap_log(TUNTAP_LOG_ERR, "Can't find a tun entry");
return -1;
default:
/* NOTREACHED */
break;
}
/* Set the interface name */
(void)memset(&ifr, 0, sizeof(ifr));
(void)snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%i", ifname, tun);
/* And save it */
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof(dev->if_name));
/* Get the interface default values */
if(ioctl(dev->ctrl_sock, SIOCGIFFLAGS, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
return fd;
}
void
tuntap_sys_destroy(struct device *dev) {
return;
tuntap_sys_destroy(struct device *dev)
{
return;
}
int
tuntap_sys_set_hwaddr(struct device *dev, struct ether_addr *eth_addr) {
struct ifreq ifr;
(void)memset(&ifr, 0, sizeof(ifr));
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof(ifr.ifr_name));
ifr.ifr_addr.sa_len = ETHER_ADDR_LEN;
ifr.ifr_addr.sa_family = AF_LINK;
(void)memcpy(ifr.ifr_addr.sa_data, eth_addr, ETHER_ADDR_LEN);
if (ioctl(dev->ctrl_sock, SIOCSIFLLADDR, &ifr) < 0) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set link-layer address");
return -1;
}
return 0;
tuntap_sys_set_ipv4_tap(struct device *dev, t_tun_in_addr *s4, uint32_t bits)
{
struct ifaliasreq ifrq;
struct sockaddr_in mask;
struct sockaddr_in addr;
struct ifreq ifr;
(void)memset(&ifrq, 0, sizeof(ifrq));
(void)strlcpy(ifrq.ifra_name, dev->if_name, sizeof(ifr.ifr_name));
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifrq);
/* Set the address */
(void)memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = s4->s_addr;
addr.sin_len = sizeof(addr);
(void)memcpy(&ifrq.ifra_addr, &addr, sizeof(addr));
/* Then set the netmask */
(void)memset(&mask, 0, sizeof(mask));
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof(mask);
(void)memcpy(&ifrq.ifra_addr, &mask, sizeof(ifrq.ifra_mask));
if(ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifrq) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP address/netmask");
return -1;
}
return 0;
}
int
tuntap_sys_set_ipv4_tap(struct device *dev, t_tun_in_addr *s4, uint32_t bits) {
struct ifaliasreq ifrq;
struct sockaddr_in mask;
struct sockaddr_in addr;
struct ifreq ifr;
(void)memset(&ifrq, 0, sizeof(ifrq));
(void)strlcpy(ifrq.ifra_name, dev->if_name, sizeof(ifr.ifr_name));
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifrq);
/* Set the address */
(void)memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = s4->s_addr;
addr.sin_len = sizeof(addr);
(void)memcpy(&ifrq.ifra_addr, &addr, sizeof(addr));
/* Then set the netmask */
(void)memset(&mask, 0, sizeof(mask));
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof(mask);
(void)memcpy(&ifrq.ifra_addr, &mask, sizeof(ifrq.ifra_mask));
if (ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifrq) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP address/netmask");
return -1;
}
return 0;
tuntap_sys_set_ipv4_tun(struct device *dev, t_tun_in_addr *s4,
t_tun_in_addr *s4dest, uint32_t bits)
{
struct ifaliasreq ifrq;
struct sockaddr_in mask;
struct sockaddr_in saddr;
struct sockaddr_in daddr;
(void)memset(&ifrq, 0, sizeof(ifrq));
(void)memcpy(ifrq.ifra_name, dev->if_name, sizeof(ifrq.ifra_name));
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifrq);
/* Set the address */
(void)memset(&saddr, 0, sizeof(saddr));
saddr.sin_family = AF_INET;
saddr.sin_addr.s_addr = s4->s_addr;
saddr.sin_len = sizeof(saddr);
(void)memcpy(&ifrq.ifra_addr, &saddr, sizeof(saddr));
(void)memset(&daddr, 0, sizeof(daddr));
daddr.sin_family = AF_INET;
daddr.sin_addr.s_addr = s4dest->s_addr;
daddr.sin_len = sizeof(daddr);
(void)memcpy(&ifrq.ifra_broadaddr, &daddr, sizeof(daddr));
/* Then set the netmask */
(void)memset(&mask, 0, sizeof(mask));
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof(mask);
(void)memcpy(&ifrq.ifra_addr, &mask, sizeof(ifrq.ifra_mask));
if(ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifrq) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP address");
return -1;
}
return 0;
}
int
tuntap_sys_set_ipv4_tun(struct device *dev, t_tun_in_addr *s4, t_tun_in_addr *s4dest, uint32_t bits) {
struct ifaliasreq ifrq;
struct sockaddr_in mask;
struct sockaddr_in saddr;
struct sockaddr_in daddr;
(void)memset(&ifrq, 0, sizeof(ifrq));
(void)memcpy(ifrq.ifra_name, dev->if_name, sizeof(ifrq.ifra_name));
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifrq);
/* Set the address */
(void)memset(&saddr, 0, sizeof(saddr));
saddr.sin_family = AF_INET;
saddr.sin_addr.s_addr = s4->s_addr;
saddr.sin_len = sizeof(saddr);
(void)memcpy(&ifrq.ifra_addr, &saddr, sizeof(saddr));
(void)memset(&daddr, 0, sizeof(daddr));
daddr.sin_family = AF_INET;
daddr.sin_addr.s_addr = s4dest->s_addr;
daddr.sin_len = sizeof(daddr);
(void)memcpy(&ifrq.ifra_broadaddr, &daddr, sizeof(daddr));
/* Then set the netmask */
(void)memset(&mask, 0, sizeof(mask));
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof(mask);
(void)memcpy(&ifrq.ifra_addr, &mask, sizeof(ifrq.ifra_mask));
if (ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifrq) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP address");
return -1;
}
return 0;
}
tuntap_sys_set_descr(struct device *dev, const char *descr, size_t len)
{
#if defined FreeBSD
struct ifreq ifr;
struct ifreq_buffer ifrbuf;
(void)memset(&ifr, 0, sizeof(ifr));
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof(ifr.ifr_name));
int
tuntap_sys_set_descr(struct device *dev, const char *descr, size_t len) {
#if defined FreeBSD
struct ifreq ifr;
struct ifreq_buffer ifrbuf;
(void)memset(&ifr, 0, sizeof(ifr));
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof(ifr.ifr_name));
ifrbuf.buffer = (void *)descr;
ifrbuf.length = len;
ifr.ifr_buffer = ifrbuf;
if (ioctl(dev->ctrl_sock, SIOCSIFDESCR, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR,
"Can't set the interface description");
return -1;
}
return 0;
ifrbuf.buffer = (void *)descr;
ifrbuf.length = len;
ifr.ifr_buffer = ifrbuf;
if(ioctl(dev->ctrl_sock, SIOCSIFDESCR, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set the interface description");
return -1;
}
return 0;
#elif defined DragonFly
tuntap_log(TUNTAP_LOG_NOTICE,
"Your system does not support tuntap_set_descr()");
return -1;
tuntap_log(TUNTAP_LOG_NOTICE,
"Your system does not support tuntap_set_descr()");
return -1;
#endif
}
@ -307,4 +279,4 @@ tuntap_sys_set_ifname(struct device *dev, const char *ifname, size_t len)
}
free(newname);
return 0;
}
}

@ -127,20 +127,6 @@ tuntap_sys_start(struct device *dev, int mode, int tun)
/* Save interface name */
(void)memcpy(dev->if_name, ifr.ifr_name, sizeof ifr.ifr_name);
/* Save pre-existing MAC address */
if(mode == TUNTAP_MODE_ETHERNET)
{
struct ifreq ifr_hw;
(void)memcpy(ifr_hw.ifr_name, dev->if_name, sizeof(dev->if_name));
if(ioctl(fd, SIOCGIFHWADDR, &ifr_hw) == -1)
{
tuntap_log(TUNTAP_LOG_WARN, "Can't get link-layer address");
return fd;
}
(void)memcpy(dev->hwaddr, ifr_hw.ifr_hwaddr.sa_data, ETH_ALEN);
}
return fd;
}
@ -153,26 +139,6 @@ tuntap_sys_destroy(struct device *dev)
}
}
int
tuntap_sys_set_hwaddr(struct device *dev, struct ether_addr *eth_addr)
{
struct ifreq ifr;
(void)memset(&ifr, '\0', sizeof ifr);
(void)memcpy(ifr.ifr_name, dev->if_name, sizeof dev->if_name);
ifr.ifr_hwaddr.sa_family = ARPHRD_ETHER;
(void)memcpy(ifr.ifr_hwaddr.sa_data, eth_addr->ether_addr_octet, 6);
/* Linux has a special flag for setting the MAC address */
if(ioctl(dev->ctrl_sock, SIOCSIFHWADDR, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set link-layer address");
return -1;
}
return 0;
}
int
tuntap_sys_set_ipv4(struct device *dev, t_tun_in_addr *s4, uint32_t bits)
{

@ -39,24 +39,23 @@
#include "tuntap.h"
static int
tuntap_sys_create_dev(struct device *dev, int mode, int tun) {
struct ifreq ifr;
char *name;
if (mode == TUNTAP_MODE_ETHERNET)
name = "tap%i";
else
name = "tun%i";
/* At this point 'tun' can't be TUNTAP_ID_ANY */
(void)memset(&ifr, '\0', sizeof ifr);
(void)snprintf(ifr.ifr_name, IF_NAMESIZE, name, tun);
if (ioctl(dev->ctrl_sock, SIOCIFCREATE, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set persistent");
return -1;
}
return 0;
tuntap_sys_create_dev(struct device *dev, int mode, int tun)
{
struct ifreq ifr;
char *name;
name = "tun%i";
/* At this point 'tun' can't be TUNTAP_ID_ANY */
(void)memset(&ifr, '\0', sizeof ifr);
(void)snprintf(ifr.ifr_name, IF_NAMESIZE, name, tun);
if(ioctl(dev->ctrl_sock, SIOCIFCREATE, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set persistent");
return -1;
}
return 0;
}
/*
@ -64,237 +63,215 @@ tuntap_sys_create_dev(struct device *dev, int mode, int tun) {
* To access /dev/tapN we have to create it before.
*/
static int
tuntap_sys_start_tap(struct device *dev, int tun) {
int fd;
struct ifreq ifr;
struct ifaddrs *ifa;
char name[IF_NAMESIZE + 5]; /* For /dev/IFNAMSIZ */
fd = -1;
(void)memset(&ifr, '\0', sizeof ifr);
(void)memset(name, '\0', sizeof name);
/* Set the device path to open */
if (tun < TUNTAP_ID_MAX) {
/* Create the wanted device */
tuntap_sys_create_dev(dev, TUNTAP_MODE_ETHERNET, tun);
(void)snprintf(name, sizeof name, "/dev/tap%i", tun);
} else if (tun == TUNTAP_ID_ANY) {
/* Or use autocloning */
(void)memcpy(name, "/dev/tap", 8);
} else {
return -1;
}
if ((fd = open(name, O_RDWR)) == -1) {
char buf[11 + MAXPATHLEN];
(void)memset(buf, 0, sizeof buf);
snprintf(buf, sizeof buf, "Can't open %s", name);
tuntap_log(TUNTAP_LOG_DEBUG, buf);
return -1;
}
/* Get the interface name */
if (ioctl(fd, TAPGIFNAME, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface name");
return -1;
}
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof dev->if_name);
/* Get the interface default values */
if (ioctl(fd, SIOCGIFFLAGS, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
/* Save pre-existing MAC address */
if (getifaddrs(&ifa) == 0) {
struct ifaddrs *pifa;
for (pifa = ifa; pifa != NULL; pifa = pifa->ifa_next) {
if (strcmp(pifa->ifa_name, dev->if_name) == 0) {
struct ether_addr eth_addr;
/*
* The MAC address is from 10 to 15.
*
* And yes, I know, the buffer is supposed
* to have a size of 14 bytes.
*/
(void)memcpy(dev->hwaddr,
pifa->ifa_addr->sa_data + 10,
ETHER_ADDR_LEN);
(void)memset(&eth_addr.ether_addr_octet, 0,
ETHER_ADDR_LEN);
(void)memcpy(&eth_addr.ether_addr_octet,
pifa->ifa_addr->sa_data + 10,
ETHER_ADDR_LEN);
break;
}
}
if (pifa == NULL)
tuntap_log(TUNTAP_LOG_WARN,
"Can't get link-layer address");
freeifaddrs(ifa);
}
return fd;
tuntap_sys_start_tap(struct device *dev, int tun)
{
int fd;
struct ifreq ifr;
struct ifaddrs *ifa;
char name[IF_NAMESIZE + 5]; /* For /dev/IFNAMSIZ */
fd = -1;
(void)memset(&ifr, '\0', sizeof ifr);
(void)memset(name, '\0', sizeof name);
/* Set the device path to open */
if(tun < TUNTAP_ID_MAX)
{
/* Create the wanted device */
tuntap_sys_create_dev(dev, TUNTAP_MODE_ETHERNET, tun);
(void)snprintf(name, sizeof name, "/dev/tap%i", tun);
}
else if(tun == TUNTAP_ID_ANY)
{
/* Or use autocloning */
(void)memcpy(name, "/dev/tap", 8);
}
else
{
return -1;
}
if((fd = open(name, O_RDWR)) == -1)
{
char buf[11 + MAXPATHLEN];
(void)memset(buf, 0, sizeof buf);
snprintf(buf, sizeof buf, "Can't open %s", name);
tuntap_log(TUNTAP_LOG_DEBUG, buf);
return -1;
}
/* Get the interface name */
if(ioctl(fd, TAPGIFNAME, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface name");
return -1;
}
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof dev->if_name);
/* Get the interface default values */
if(ioctl(fd, SIOCGIFFLAGS, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
return fd;
}
static int
tuntap_sys_start_tun(struct device *dev, int tun) {
struct ifreq ifr;
char name[MAXPATHLEN];
int fd;
/*
* Try to use the given driver, or loop throught the avaible ones
*/
fd = -1;
if (tun < TUNTAP_ID_MAX) {
(void)snprintf(name, sizeof name, "/dev/tun%i", tun);
fd = open(name, O_RDWR);
} else if (tun == TUNTAP_ID_ANY) {
for (tun = 0; tun < TUNTAP_ID_MAX; ++tun) {
(void)memset(name, '\0', sizeof name);
(void)snprintf(name, sizeof name, "/dev/tun%i", tun);
if ((fd = open(name, O_RDWR)) > 0)
break;
}
} else {
return -1;
}
switch (fd) {
case -1:
tuntap_log(TUNTAP_LOG_ERR, "Permission denied");
return -1;
case 256:
tuntap_log(TUNTAP_LOG_ERR, "Can't find a tun entry");
return -1;
default:
/* NOTREACHED */
break;
}
/* Set the interface name */
(void)memset(&ifr, '\0', sizeof ifr);
(void)snprintf(ifr.ifr_name, sizeof ifr.ifr_name, "tun%i", tun);
/* And save it */
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof dev->if_name);
/* Get the interface default values */
if (ioctl(dev->ctrl_sock, SIOCGIFFLAGS, &ifr) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
return fd;
tuntap_sys_start_tun(struct device *dev, int tun)
{
struct ifreq ifr;
char name[MAXPATHLEN];
int fd;
/*
* Try to use the given driver, or loop throught the avaible ones
*/
fd = -1;
if(tun < TUNTAP_ID_MAX)
{
(void)snprintf(name, sizeof name, "/dev/tun%i", tun);
fd = open(name, O_RDWR);
}
else if(tun == TUNTAP_ID_ANY)
{
for(tun = 0; tun < TUNTAP_ID_MAX; ++tun)
{
(void)memset(name, '\0', sizeof name);
(void)snprintf(name, sizeof name, "/dev/tun%i", tun);
if((fd = open(name, O_RDWR)) > 0)
break;
}
}
else
{
return -1;
}
switch(fd)
{
case -1:
tuntap_log(TUNTAP_LOG_ERR, "Permission denied");
return -1;
case 256:
tuntap_log(TUNTAP_LOG_ERR, "Can't find a tun entry");
return -1;
default:
/* NOTREACHED */
break;
}
/* Set the interface name */
(void)memset(&ifr, '\0', sizeof ifr);
(void)snprintf(ifr.ifr_name, sizeof ifr.ifr_name, "tun%i", tun);
/* And save it */
(void)strlcpy(dev->if_name, ifr.ifr_name, sizeof dev->if_name);
/* Get the interface default values */
if(ioctl(dev->ctrl_sock, SIOCGIFFLAGS, &ifr) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't get interface values");
return -1;
}
/* Save flags for tuntap_{up, down} */
dev->flags = ifr.ifr_flags;
return fd;
}
int
tuntap_sys_start(struct device *dev, int mode, int tun) {
int fd;
/* Force creation of the driver if needed or let it resilient */
if (mode & TUNTAP_MODE_PERSIST) {
mode &= ~TUNTAP_MODE_PERSIST;
if (tuntap_sys_create_dev(dev, mode, tun) == -1)
return -1;
}
/* tun and tap devices are not created in the same way */
if (mode == TUNTAP_MODE_ETHERNET) {
fd = tuntap_sys_start_tap(dev, tun);
}
else if (mode == TUNTAP_MODE_TUNNEL) {
fd = tuntap_sys_start_tun(dev, tun);
}
else {
return -1;
}
return fd;
tuntap_sys_start(struct device *dev, int mode, int tun)
{
int fd;
/* Force creation of the driver if needed or let it resilient */
if(mode & TUNTAP_MODE_PERSIST)
{
mode &= ~TUNTAP_MODE_PERSIST;
if(tuntap_sys_create_dev(dev, mode, tun) == -1)
return -1;
}
/* tun and tap devices are not created in the same way */
if(mode == TUNTAP_MODE_ETHERNET)
{
fd = tuntap_sys_start_tap(dev, tun);
}
else if(mode == TUNTAP_MODE_TUNNEL)
{
fd = tuntap_sys_start_tun(dev, tun);
}
else
{
return -1;
}
return fd;
}
void
tuntap_sys_destroy(struct device *dev) {
struct ifreq ifr;
tuntap_sys_destroy(struct device *dev)
{
struct ifreq ifr;
(void)memset(&ifr, '\0', sizeof ifr);
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof ifr.ifr_name);
(void)memset(&ifr, '\0', sizeof ifr);
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof ifr.ifr_name);
if (ioctl(dev->ctrl_sock, SIOCIFDESTROY, &ifr) == -1)
tuntap_log(TUNTAP_LOG_WARN, "Can't destroy the interface");
if(ioctl(dev->ctrl_sock, SIOCIFDESTROY, &ifr) == -1)
tuntap_log(TUNTAP_LOG_WARN, "Can't destroy the interface");
}
int
tuntap_sys_set_hwaddr(struct device *dev, struct ether_addr *eth_addr) {
struct ifaliasreq ifra;
(void)memset(&ifra, 0, sizeof ifra);
(void)memcpy(ifra.ifra_name, dev->if_name, sizeof dev->if_name);
ifra.ifra_addr.sa_len = ETHER_ADDR_LEN;
ifra.ifra_addr.sa_family = AF_LINK;
(void)memcpy(ifra.ifra_addr.sa_data, eth_addr, ETHER_ADDR_LEN);
if (ioctl(dev->ctrl_sock, SIOCSIFPHYADDR, &ifra) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set link-layer address");
return -1;
}
return 0;
tuntap_sys_set_ipv4(struct device *dev, t_tun_in_addr *s, uint32_t bits)
{
struct ifaliasreq ifa;
struct ifreq ifr;
struct sockaddr_in mask;
struct sockaddr_in addr;
(void)memset(&ifa, '\0', sizeof ifa);
(void)strlcpy(ifa.ifra_name, dev->if_name, sizeof ifa.ifra_name);
(void)memset(&ifr, '\0', sizeof ifr);
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof ifr.ifr_name);
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifr);
/*
* Fill-in the destination address and netmask,
* but don't care of the broadcast address
*/
(void)memset(&addr, '\0', sizeof addr);
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = s->s_addr;
addr.sin_len = sizeof addr;
(void)memcpy(&ifa.ifra_addr, &addr, sizeof addr);
(void)memset(&mask, '\0', sizeof mask);
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof mask;
(void)memcpy(&ifa.ifra_mask, &mask, sizeof ifa.ifra_mask);
/* Simpler than calling SIOCSIFADDR and/or SIOCSIFBRDADDR */
if(ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifa) == -1)
{
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP/netmask");
return -1;
}
return 0;
}
int
tuntap_sys_set_ipv4(struct device *dev, t_tun_in_addr *s, uint32_t bits) {
struct ifaliasreq ifa;
struct ifreq ifr;
struct sockaddr_in mask;
struct sockaddr_in addr;
(void)memset(&ifa, '\0', sizeof ifa);
(void)strlcpy(ifa.ifra_name, dev->if_name, sizeof ifa.ifra_name);
(void)memset(&ifr, '\0', sizeof ifr);
(void)strlcpy(ifr.ifr_name, dev->if_name, sizeof ifr.ifr_name);
/* Delete previously assigned address */
(void)ioctl(dev->ctrl_sock, SIOCDIFADDR, &ifr);
/*
* Fill-in the destination address and netmask,
* but don't care of the broadcast address
*/
(void)memset(&addr, '\0', sizeof addr);
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = s->s_addr;
addr.sin_len = sizeof addr;
(void)memcpy(&ifa.ifra_addr, &addr, sizeof addr);
(void)memset(&mask, '\0', sizeof mask);
mask.sin_family = AF_INET;
mask.sin_addr.s_addr = bits;
mask.sin_len = sizeof mask;
(void)memcpy(&ifa.ifra_mask, &mask, sizeof ifa.ifra_mask);
/* Simpler than calling SIOCSIFADDR and/or SIOCSIFBRDADDR */
if (ioctl(dev->ctrl_sock, SIOCAIFADDR, &ifa) == -1) {
tuntap_log(TUNTAP_LOG_ERR, "Can't set IP/netmask");
return -1;
}
return 0;
tuntap_sys_set_descr(struct device *dev, const char *descr, size_t len)
{
tuntap_log(TUNTAP_LOG_NOTICE,
"Your system does not support tuntap_set_descr()");
return -1;
}
int
tuntap_sys_set_descr(struct device *dev, const char *descr, size_t len) {
tuntap_log(TUNTAP_LOG_NOTICE,
"Your system does not support tuntap_set_descr()");
return -1;
}

@ -168,52 +168,6 @@ tuntap_set_ifname(struct device *dev, const char *ifname)
return 0;
}
char *
tuntap_get_hwaddr(struct device *dev)
{
struct ether_addr eth_attr;
(void)memcpy(&eth_attr, dev->hwaddr, sizeof dev->hwaddr);
return ether_ntoa(&eth_attr);
}
int
tuntap_set_hwaddr(struct device *dev, const char *hwaddr)
{
struct ether_addr *eth_addr, eth_rand;
if(strcmp(hwaddr, "random") == 0)
{
unsigned int i;
unsigned char *ptr;
i = 0;
ptr = (unsigned char *)&eth_rand;
srandom((unsigned int)time(NULL));
for(; i < sizeof eth_rand; ++i)
{
*ptr = (unsigned char)random();
ptr++;
}
ptr = (unsigned char *)&eth_rand;
*ptr &= 0xfc;
eth_addr = &eth_rand;
}
else
{
eth_addr = ether_aton(hwaddr);
if(eth_addr == NULL)
{
return -1;
}
}
(void)memcpy(dev->hwaddr, eth_addr, ETHER_ADDR_LEN);
if(tuntap_sys_set_hwaddr(dev, eth_addr) == -1)
return -1;
return 0;
}
int
tuntap_up(struct device *dev)
{

@ -59,7 +59,6 @@ extern "C"
return NULL;
(void)memset(dev->if_name, '\0', sizeof(dev->if_name));
(void)memset(dev->hwaddr, '\0', sizeof(dev->hwaddr));
dev->tun_fd = TUNFD_INVALID_VALUE;
dev->ctrl_sock = -1;
dev->flags = 0;
@ -88,7 +87,8 @@ extern "C"
}
int
tuntap_set_ip(struct device *dev, const char *addr, const char *daddr, int netmask)
tuntap_set_ip(struct device *dev, const char *addr, const char *daddr,
int netmask)
{
t_tun_in_addr baddr4;
t_tun_in6_addr baddr6;

Loading…
Cancel
Save