mirror of
https://github.com/neocturne/fastd.git
synced 2025-05-14 12:25:07 +02:00
iface: make fastd_iface_open() gracefully (at least on Linux, for now)
This commit is contained in:
parent
0e8493ea17
commit
6dbb8e041c
3 changed files with 43 additions and 17 deletions
|
@ -176,11 +176,12 @@ int fastd_android_receive_tunfd(void) {
|
||||||
|
|
||||||
int handle;
|
int handle;
|
||||||
if (ancil_recv_fd(ctx.android_ctrl_sock_fd, &handle)) {
|
if (ancil_recv_fd(ctx.android_ctrl_sock_fd, &handle)) {
|
||||||
exit_errno("could not receive TUN handle from Android");
|
pr_error("could not receive TUN handle from Android");
|
||||||
} else {
|
return -1;
|
||||||
pr_debug("received fd: %u", handle);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pr_debug("received fd: %u", handle);
|
||||||
|
|
||||||
return handle;
|
return handle;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -500,8 +500,11 @@ static inline void init(int argc, char *argv[]) {
|
||||||
|
|
||||||
fastd_on_pre_up();
|
fastd_on_pre_up();
|
||||||
|
|
||||||
if (conf.mode == MODE_TAP)
|
if (conf.mode == MODE_TAP) {
|
||||||
ctx.iface = fastd_iface_open(NULL);
|
ctx.iface = fastd_iface_open(NULL);
|
||||||
|
if (!ctx.iface)
|
||||||
|
exit(1); /* An error message has already been printed by fastd_iface_open() */
|
||||||
|
}
|
||||||
|
|
||||||
/* change groups before trying to write the PID file as they can be relevant for file access */
|
/* change groups before trying to write the PID file as they can be relevant for file access */
|
||||||
set_groups();
|
set_groups();
|
||||||
|
|
48
src/iface.c
48
src/iface.c
|
@ -85,16 +85,19 @@ static inline fastd_iface_type_t get_iface_type(void) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void open_iface(fastd_iface_t *iface);
|
||||||
|
|
||||||
|
|
||||||
#ifdef __linux__
|
#ifdef __linux__
|
||||||
|
|
||||||
/** Opens the TUN/TAP device helper shared by Android and Linux targets */
|
/** Opens the TUN/TAP device helper shared by Android and Linux targets */
|
||||||
static void open_iface_linux(fastd_iface_t *iface, const char *dev_name) {
|
static void open_iface_linux(fastd_iface_t *iface, const char *dev_name) {
|
||||||
|
int ctl_sock = -1;
|
||||||
struct ifreq ifr = {};
|
struct ifreq ifr = {};
|
||||||
|
|
||||||
iface->fd = FASTD_POLL_FD(POLL_TYPE_IFACE, open(dev_name, O_RDWR|O_NONBLOCK));
|
iface->fd = FASTD_POLL_FD(POLL_TYPE_IFACE, open(dev_name, O_RDWR|O_NONBLOCK));
|
||||||
if (iface->fd.fd < 0)
|
if (iface->fd.fd < 0)
|
||||||
exit_errno("could not open tun/tap device file");
|
exit_errno("could not open TUN/TAP device file");
|
||||||
|
|
||||||
if (conf.ifname)
|
if (conf.ifname)
|
||||||
strncpy(ifr.ifr_name, conf.ifname, IFNAMSIZ-1);
|
strncpy(ifr.ifr_name, conf.ifname, IFNAMSIZ-1);
|
||||||
|
@ -113,12 +116,14 @@ static void open_iface_linux(fastd_iface_t *iface, const char *dev_name) {
|
||||||
}
|
}
|
||||||
|
|
||||||
ifr.ifr_flags |= IFF_NO_PI;
|
ifr.ifr_flags |= IFF_NO_PI;
|
||||||
if (ioctl(iface->fd.fd, TUNSETIFF, &ifr) < 0)
|
if (ioctl(iface->fd.fd, TUNSETIFF, &ifr) < 0) {
|
||||||
exit_errno("TUNSETIFF ioctl failed");
|
pr_error_errno("unable to open TUN/TAP interface: TUNSETIFF ioctl failed");
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
|
|
||||||
iface->name = fastd_strndup(ifr.ifr_name, IFNAMSIZ-1);
|
iface->name = fastd_strndup(ifr.ifr_name, IFNAMSIZ-1);
|
||||||
|
|
||||||
int ctl_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP);
|
ctl_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP);
|
||||||
if (ctl_sock < 0)
|
if (ctl_sock < 0)
|
||||||
exit_errno("socket");
|
exit_errno("socket");
|
||||||
|
|
||||||
|
@ -127,13 +132,25 @@ static void open_iface_linux(fastd_iface_t *iface, const char *dev_name) {
|
||||||
|
|
||||||
if (ifr.ifr_mtu != conf.mtu) {
|
if (ifr.ifr_mtu != conf.mtu) {
|
||||||
ifr.ifr_mtu = conf.mtu;
|
ifr.ifr_mtu = conf.mtu;
|
||||||
if (ioctl(ctl_sock, SIOCSIFMTU, &ifr) < 0)
|
if (ioctl(ctl_sock, SIOCSIFMTU, &ifr) < 0) {
|
||||||
exit_errno("SIOCSIFMTU ioctl failed");
|
pr_error_errno("unable to set TUN/TAP interface MTU: SIOCSIFMTU ioctl failed");
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (close(ctl_sock))
|
if (close(ctl_sock))
|
||||||
pr_error_errno("close");
|
pr_error_errno("close");
|
||||||
|
|
||||||
|
return;
|
||||||
|
|
||||||
|
error:
|
||||||
|
if (ctl_sock >= 0) {
|
||||||
|
if (close(ctl_sock))
|
||||||
|
pr_error_errno("close");
|
||||||
|
}
|
||||||
|
|
||||||
|
close(iface->fd.fd);
|
||||||
|
iface->fd.fd = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -247,10 +264,10 @@ static void open_iface(fastd_iface_t *iface) {
|
||||||
|
|
||||||
iface->fd = FASTD_POLL_FD(POLL_TYPE_IFACE, open(ifname, O_RDWR|O_NONBLOCK));
|
iface->fd = FASTD_POLL_FD(POLL_TYPE_IFACE, open(ifname, O_RDWR|O_NONBLOCK));
|
||||||
if (iface->fd.fd < 0)
|
if (iface->fd.fd < 0)
|
||||||
exit_errno("could not open tun/tap device file");
|
exit_errno("could not open TUN/TAP device file");
|
||||||
|
|
||||||
if (!(iface->name = fdevname_r(iface->fd.fd, fastd_alloc(IFNAMSIZ), IFNAMSIZ)))
|
if (!(iface->name = fdevname_r(iface->fd.fd, fastd_alloc(IFNAMSIZ), IFNAMSIZ)))
|
||||||
exit_errno("could not get tun/tap interface name");
|
exit_errno("could not get TUN/TAP interface name");
|
||||||
|
|
||||||
switch (get_iface_type()) {
|
switch (get_iface_type()) {
|
||||||
case IFACE_TYPE_TAP:
|
case IFACE_TYPE_TAP:
|
||||||
|
@ -383,7 +400,7 @@ static void open_iface(fastd_iface_t *iface) {
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
#error unknown tun/tap implementation
|
#error unknown TUN/TAP implementation
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -448,13 +465,18 @@ fastd_iface_t * fastd_iface_open(fastd_peer_t *peer) {
|
||||||
fastd_iface_t *iface = fastd_new(fastd_iface_t);
|
fastd_iface_t *iface = fastd_new(fastd_iface_t);
|
||||||
iface->peer = peer;
|
iface->peer = peer;
|
||||||
|
|
||||||
pr_debug("initializing tun/tap device...");
|
pr_debug("initializing TUN/TAP device...");
|
||||||
open_iface(iface);
|
open_iface(iface);
|
||||||
|
|
||||||
|
if (iface->fd.fd < 0) {
|
||||||
|
free(iface);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
if (iface->name)
|
if (iface->name)
|
||||||
pr_debug("tun/tap device `%s' initialized.", iface->name);
|
pr_debug("TUN/TAP device `%s' initialized.", iface->name);
|
||||||
else
|
else
|
||||||
pr_debug("tun/tap device initialized.");
|
pr_debug("TUN/TAP device initialized.");
|
||||||
|
|
||||||
fastd_poll_fd_register(&iface->fd);
|
fastd_poll_fd_register(&iface->fd);
|
||||||
|
|
||||||
|
@ -464,7 +486,7 @@ fastd_iface_t * fastd_iface_open(fastd_peer_t *peer) {
|
||||||
/** Closes the TUN/TAP device */
|
/** Closes the TUN/TAP device */
|
||||||
void fastd_iface_close(fastd_iface_t *iface) {
|
void fastd_iface_close(fastd_iface_t *iface) {
|
||||||
if (!fastd_poll_fd_close(&iface->fd))
|
if (!fastd_poll_fd_close(&iface->fd))
|
||||||
pr_warn_errno("closing tun/tap: close");
|
pr_warn_errno("closing TUN/TAP: close");
|
||||||
|
|
||||||
free(iface->name);
|
free(iface->name);
|
||||||
free(iface);
|
free(iface);
|
||||||
|
|
Loading…
Add table
Reference in a new issue