summaryrefslogtreecommitdiffstats
path: root/usr.sbin/sasyncd/net.c
diff options
context:
space:
mode:
authorho <ho@openbsd.org>2005-05-23 17:35:01 +0000
committerho <ho@openbsd.org>2005-05-23 17:35:01 +0000
commit6db4730e6571984798299956b5b7454ec7f7059f (patch)
treea749ce734d0ef46f1632c517f4c7d63494f50c26 /usr.sbin/sasyncd/net.c
parentNo more SSL. Make text somewhat clearer. (diff)
downloadwireguard-openbsd-6db4730e6571984798299956b5b7454ec7f7059f.tar.xz
wireguard-openbsd-6db4730e6571984798299956b5b7454ec7f7059f.zip
add "listen on <interface name>"
Diffstat (limited to 'usr.sbin/sasyncd/net.c')
-rw-r--r--usr.sbin/sasyncd/net.c91
1 files changed, 71 insertions, 20 deletions
diff --git a/usr.sbin/sasyncd/net.c b/usr.sbin/sasyncd/net.c
index 637f3f3258a..d38eb2b379b 100644
--- a/usr.sbin/sasyncd/net.c
+++ b/usr.sbin/sasyncd/net.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: net.c,v 1.2 2005/05/22 20:35:48 ho Exp $ */
+/* $OpenBSD: net.c,v 1.3 2005/05/23 17:35:01 ho Exp $ */
/*
* Copyright (c) 2005 Håkan Olsson. All rights reserved.
@@ -35,6 +35,8 @@
#include <sys/time.h>
#include <netinet/in.h>
#include <arpa/inet.h>
+#include <ifaddrs.h>
+#include <netdb.h>
#include <openssl/aes.h>
#include <openssl/sha.h>
@@ -91,10 +93,11 @@ net_init(void)
struct sockaddr_storage sa_storage;
struct sockaddr *sa = (struct sockaddr *)&sa_storage;
struct syncpeer *p;
+ char host[NI_MAXHOST], port[NI_MAXSERV];
int r;
/* The shared key needs to be 128, 192 or 256 bits */
- r = (strlen(cfgstate.sharedkey) - 1) << 3;
+ r = strlen(cfgstate.sharedkey) << 3;
if (r != 128 && r != 192 && r != 256) {
fprintf(stderr, "Bad shared key length (%d bits), "
"should be 128, 192 or 256\n", r);
@@ -110,9 +113,11 @@ net_init(void)
/* Setup listening socket. */
memset(&sa_storage, 0, sizeof sa_storage);
if (net_set_sa(sa, cfgstate.listen_on, cfgstate.listen_port)) {
- perror("inet_pton");
+ log_msg(0, "net_init: could not find listen address (%s)",
+ cfgstate.listen_on);
return -1;
}
+
listen_socket = socket(sa->sa_family, SOCK_STREAM, 0);
if (listen_socket < 0) {
perror("socket()");
@@ -137,8 +142,14 @@ net_init(void)
close(listen_socket);
return -1;
}
- log_msg(2, "listening on port %u fd %d", cfgstate.listen_port,
- listen_socket);
+
+ if (getnameinfo(sa, sa->sa_len, host, sizeof host, port, sizeof port,
+ NI_NUMERICHOST | NI_NUMERICSERV))
+ log_msg(2, "listening on port %u fd %d", cfgstate.listen_port,
+ listen_socket);
+ else
+ log_msg(2, "listening on %s port %s fd %d", host, port,
+ listen_socket);
for (p = LIST_FIRST(&cfgstate.peerlist); p; p = LIST_NEXT(p, link)) {
p->socket = -1;
@@ -576,31 +587,71 @@ net_set_sa(struct sockaddr *sa, char *name, in_port_t port)
{
struct sockaddr_in *sin = (struct sockaddr_in *)sa;
struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)sa;
+ struct ifaddrs *ifap, *ifa;
+
+ if (!name) {
+ /* XXX Assume IPv4 */
+ sa->sa_family = AF_INET;
+ sin->sin_port = htons(port);
+ sin->sin_len = sizeof *sin;
+ return 0;
+ }
- if (name) {
- if (inet_pton(AF_INET, name, &sin->sin_addr) == 1) {
+ if (inet_pton(AF_INET, name, &sin->sin_addr) == 1) {
+ sa->sa_family = AF_INET;
+ sin->sin_port = htons(port);
+ sin->sin_len = sizeof *sin;
+ return 0;
+ }
+
+ if (inet_pton(AF_INET6, name, &sin6->sin6_addr) == 1) {
+ sa->sa_family = AF_INET6;
+ sin6->sin6_port = htons(port);
+ sin6->sin6_len = sizeof *sin6;
+ return 0;
+ }
+
+ /* inet_pton failed. fail here if name is not cfgstate.listen_on */
+ if (strcmp(cfgstate.listen_on, name) != 0)
+ return -1;
+
+ /* Is cfgstate.listen_on the name of one our interfaces? */
+ if (getifaddrs(&ifap) != 0) {
+ perror("getifaddrs()");
+ return -1;
+ }
+ sa->sa_family = AF_UNSPEC;
+ for (ifa = ifap; ifa && sa->sa_family == AF_UNSPEC;
+ ifa = ifa->ifa_next) {
+ if (!ifa->ifa_name || !ifa->ifa_addr)
+ continue;
+ if (strcmp(ifa->ifa_name, name) != 0)
+ continue;
+
+ switch (ifa->ifa_addr->sa_family) {
+ case AF_INET:
sa->sa_family = AF_INET;
sin->sin_port = htons(port);
sin->sin_len = sizeof *sin;
- return 0;
- }
-
- if (inet_pton(AF_INET6, name, &sin6->sin6_addr) == 1) {
+ memcpy(&sin->sin_addr,
+ &((struct sockaddr_in *)ifa->ifa_addr)->sin_addr,
+ sizeof sin->sin_addr);
+ break;
+
+ case AF_INET6:
sa->sa_family = AF_INET6;
sin6->sin6_port = htons(port);
sin6->sin6_len = sizeof *sin6;
- return 0;
+ memcpy(&sin6->sin6_addr,
+ &((struct sockaddr_in6 *)ifa->ifa_addr)->sin6_addr,
+ sizeof sin6->sin6_addr);
+ break;
}
- } else {
- /* XXX Assume IPv4 */
- sa->sa_family = AF_INET;
- sin->sin_port = htons(port);
- sin->sin_len = sizeof *sin;
- return 0;
}
-
- return 1;
+ freeifaddrs(ifap);
+ return sa->sa_family == AF_UNSPEC ? -1 : 0;
}
+
static void
got_sigalrm(int s)