Capsicumize ping6
Add capsicum support to ping6, mostly copying the strategy used for ping. Submitted by: Ján Sučan <jansucan@gmail.com> Reviewed by: markj MFC after: 2 weeks Sponsored by: Google, inc. (Google Summer of Code 2019) Differential Revision: https://reviews.freebsd.org/D21050
This commit is contained in:
parent
ea44065c1f
commit
2943ddcf51
@ -1,5 +1,7 @@
|
||||
# $FreeBSD$
|
||||
|
||||
.include <src.opts.mk>
|
||||
|
||||
PACKAGE=runtime
|
||||
PROG= ping6
|
||||
MAN= ping6.8
|
||||
@ -12,4 +14,12 @@ BINMODE=4555
|
||||
|
||||
LIBADD= ipsec m md
|
||||
|
||||
.if ${MK_DYNAMICROOT} == "no"
|
||||
.warning ${PROG} built without libcasper support
|
||||
.elif ${MK_CASPER} != "no" && !defined(RESCUE)
|
||||
LIBADD+= casper
|
||||
LIBADD+= cap_dns
|
||||
CFLAGS+=-DWITH_CASPER
|
||||
.endif
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
@ -104,6 +104,7 @@ __FBSDID("$FreeBSD$");
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/capsicum.h>
|
||||
#include <sys/uio.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/time.h>
|
||||
@ -118,6 +119,10 @@ __FBSDID("$FreeBSD$");
|
||||
#include <arpa/nameser.h>
|
||||
#include <netdb.h>
|
||||
|
||||
#include <capsicum_helpers.h>
|
||||
#include <casper/cap_dns.h>
|
||||
#include <libcasper.h>
|
||||
|
||||
#include <ctype.h>
|
||||
#include <err.h>
|
||||
#include <errno.h>
|
||||
@ -214,7 +219,8 @@ static struct sockaddr_in6 dst; /* who to ping6 */
|
||||
static struct sockaddr_in6 src; /* src addr of this packet */
|
||||
static socklen_t srclen;
|
||||
static size_t datalen = DEFDATALEN;
|
||||
static int s; /* socket file descriptor */
|
||||
static int ssend; /* send socket file descriptor */
|
||||
static int srecv; /* receive socket file descriptor */
|
||||
static u_char outpack[MAXPACKETLEN];
|
||||
static char BSPACE = '\b'; /* characters written for flood */
|
||||
static char BBELL = '\a'; /* characters written for AUDIBLE */
|
||||
@ -224,6 +230,7 @@ static int ident; /* process id to identify our packets */
|
||||
static u_int8_t nonce[8]; /* nonce field for node information */
|
||||
static int hoplimit = -1; /* hoplimit */
|
||||
static u_char *packet = NULL;
|
||||
static cap_channel_t *capdns;
|
||||
|
||||
/* counters */
|
||||
static long nmissedmax; /* max value of ntransmitted - nreceived - 1 */
|
||||
@ -256,6 +263,7 @@ static volatile sig_atomic_t seeninfo;
|
||||
#endif
|
||||
|
||||
int main(int, char *[]);
|
||||
static cap_channel_t *capdns_setup(void);
|
||||
static void fill(char *, char *);
|
||||
static int get_hoplim(struct msghdr *);
|
||||
static int get_pathmtu(struct msghdr *);
|
||||
@ -318,6 +326,9 @@ main(int argc, char *argv[])
|
||||
#ifdef IPV6_USE_MIN_MTU
|
||||
int mflag = 0;
|
||||
#endif
|
||||
cap_rights_t rights_srecv;
|
||||
cap_rights_t rights_ssend;
|
||||
cap_rights_t rights_stdin;
|
||||
|
||||
/* just to be sure */
|
||||
memset(&smsghdr, 0, sizeof(smsghdr));
|
||||
@ -325,6 +336,7 @@ main(int argc, char *argv[])
|
||||
|
||||
alarmtimeout = preload = 0;
|
||||
datap = &outpack[ICMP6ECHOLEN + ICMP6ECHOTMLEN];
|
||||
capdns = capdns_setup();
|
||||
#ifndef IPSEC
|
||||
#define ADDOPTS
|
||||
#else
|
||||
@ -503,7 +515,7 @@ main(int argc, char *argv[])
|
||||
hints.ai_socktype = SOCK_RAW;
|
||||
hints.ai_protocol = IPPROTO_ICMPV6;
|
||||
|
||||
error = getaddrinfo(optarg, NULL, &hints, &res);
|
||||
error = cap_getaddrinfo(capdns, optarg, NULL, &hints, &res);
|
||||
if (error) {
|
||||
errx(1, "invalid source address: %s",
|
||||
gai_strerror(error));
|
||||
@ -619,14 +631,14 @@ main(int argc, char *argv[])
|
||||
} else
|
||||
target = argv[argc - 1];
|
||||
|
||||
/* getaddrinfo */
|
||||
/* cap_getaddrinfo */
|
||||
memset(&hints, 0, sizeof(struct addrinfo));
|
||||
hints.ai_flags = AI_CANONNAME;
|
||||
hints.ai_family = AF_INET6;
|
||||
hints.ai_socktype = SOCK_RAW;
|
||||
hints.ai_protocol = IPPROTO_ICMPV6;
|
||||
|
||||
error = getaddrinfo(target, NULL, &hints, &res);
|
||||
error = cap_getaddrinfo(capdns, target, NULL, &hints, &res);
|
||||
if (error)
|
||||
errx(1, "%s", gai_strerror(error));
|
||||
if (res->ai_canonname)
|
||||
@ -635,13 +647,16 @@ main(int argc, char *argv[])
|
||||
hostname = target;
|
||||
|
||||
if (!res->ai_addr)
|
||||
errx(1, "getaddrinfo failed");
|
||||
errx(1, "cap_getaddrinfo failed");
|
||||
|
||||
(void)memcpy(&dst, res->ai_addr, res->ai_addrlen);
|
||||
|
||||
if ((s = socket(res->ai_family, res->ai_socktype,
|
||||
if ((ssend = socket(res->ai_family, res->ai_socktype,
|
||||
res->ai_protocol)) < 0)
|
||||
err(1, "socket");
|
||||
err(1, "socket ssend");
|
||||
if ((srecv = socket(res->ai_family, res->ai_socktype,
|
||||
res->ai_protocol)) < 0)
|
||||
err(1, "socket srecv");
|
||||
freeaddrinfo(res);
|
||||
|
||||
/* set the source address if specified. */
|
||||
@ -656,7 +671,7 @@ main(int argc, char *argv[])
|
||||
if (dst.sin6_scope_id == 0)
|
||||
dst.sin6_scope_id = src.sin6_scope_id;
|
||||
}
|
||||
if (bind(s, (struct sockaddr *)&src, srclen) != 0)
|
||||
if (bind(ssend, (struct sockaddr *)&src, srclen) != 0)
|
||||
err(1, "bind");
|
||||
}
|
||||
/* set the gateway (next hop) if specified */
|
||||
@ -666,15 +681,15 @@ main(int argc, char *argv[])
|
||||
hints.ai_socktype = SOCK_RAW;
|
||||
hints.ai_protocol = IPPROTO_ICMPV6;
|
||||
|
||||
error = getaddrinfo(gateway, NULL, &hints, &res);
|
||||
error = cap_getaddrinfo(capdns, gateway, NULL, &hints, &res);
|
||||
if (error) {
|
||||
errx(1, "getaddrinfo for the gateway %s: %s",
|
||||
errx(1, "cap_getaddrinfo for the gateway %s: %s",
|
||||
gateway, gai_strerror(error));
|
||||
}
|
||||
if (res->ai_next && (options & F_VERBOSE))
|
||||
warnx("gateway resolves to multiple addresses");
|
||||
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_NEXTHOP,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_NEXTHOP,
|
||||
res->ai_addr, res->ai_addrlen)) {
|
||||
err(1, "setsockopt(IPV6_NEXTHOP)");
|
||||
}
|
||||
@ -690,25 +705,25 @@ main(int argc, char *argv[])
|
||||
int opton = 1;
|
||||
|
||||
#ifdef IPV6_RECVHOPOPTS
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVHOPOPTS, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVHOPOPTS, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_RECVHOPOPTS)");
|
||||
#else /* old adv. API */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_HOPOPTS, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_HOPOPTS, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_HOPOPTS)");
|
||||
#endif
|
||||
#ifdef IPV6_RECVDSTOPTS
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVDSTOPTS, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVDSTOPTS, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_RECVDSTOPTS)");
|
||||
#else /* old adv. API */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_DSTOPTS, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_DSTOPTS, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_DSTOPTS)");
|
||||
#endif
|
||||
#ifdef IPV6_RECVRTHDRDSTOPTS
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVRTHDRDSTOPTS, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVRTHDRDSTOPTS, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_RECVRTHDRDSTOPTS)");
|
||||
#endif
|
||||
@ -751,31 +766,34 @@ main(int argc, char *argv[])
|
||||
arc4random_buf(nonce, sizeof(nonce));
|
||||
optval = 1;
|
||||
if (options & F_DONTFRAG)
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_DONTFRAG,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_DONTFRAG,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "IPV6_DONTFRAG");
|
||||
hold = 1;
|
||||
|
||||
if (options & F_SO_DEBUG)
|
||||
(void)setsockopt(s, SOL_SOCKET, SO_DEBUG, (char *)&hold,
|
||||
if (options & F_SO_DEBUG) {
|
||||
(void)setsockopt(ssend, SOL_SOCKET, SO_DEBUG, (char *)&hold,
|
||||
sizeof(hold));
|
||||
(void)setsockopt(srecv, SOL_SOCKET, SO_DEBUG, (char *)&hold,
|
||||
sizeof(hold));
|
||||
}
|
||||
optval = IPV6_DEFHLIM;
|
||||
if (IN6_IS_ADDR_MULTICAST(&dst.sin6_addr))
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_MULTICAST_HOPS,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_MULTICAST_HOPS,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "IPV6_MULTICAST_HOPS");
|
||||
#ifdef IPV6_USE_MIN_MTU
|
||||
if (mflag != 1) {
|
||||
optval = mflag > 1 ? 0 : 1;
|
||||
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_USE_MIN_MTU,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_USE_MIN_MTU,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_USE_MIN_MTU)");
|
||||
}
|
||||
#ifdef IPV6_RECVPATHMTU
|
||||
else {
|
||||
optval = 1;
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVPATHMTU,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVPATHMTU,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_RECVPATHMTU)");
|
||||
}
|
||||
@ -785,27 +803,36 @@ main(int argc, char *argv[])
|
||||
#ifdef IPSEC
|
||||
#ifdef IPSEC_POLICY_IPSEC
|
||||
if (options & F_POLICY) {
|
||||
if (setpolicy(s, policy_in) < 0)
|
||||
if (setpolicy(srecv, policy_in) < 0)
|
||||
errx(1, "%s", ipsec_strerror());
|
||||
if (setpolicy(s, policy_out) < 0)
|
||||
if (setpolicy(ssend, policy_out) < 0)
|
||||
errx(1, "%s", ipsec_strerror());
|
||||
}
|
||||
#else
|
||||
if (options & F_AUTHHDR) {
|
||||
optval = IPSEC_LEVEL_REQUIRE;
|
||||
#ifdef IPV6_AUTH_TRANS_LEVEL
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_AUTH_TRANS_LEVEL,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_AUTH_TRANS_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_AUTH_TRANS_LEVEL)");
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_AUTH_TRANS_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_AUTH_TRANS_LEVEL)");
|
||||
#else /* old def */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_AUTH_LEVEL,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_AUTH_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_AUTH_LEVEL)");
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_AUTH_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_AUTH_LEVEL)");
|
||||
#endif
|
||||
}
|
||||
if (options & F_ENCRYPT) {
|
||||
optval = IPSEC_LEVEL_REQUIRE;
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_ESP_TRANS_LEVEL,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_ESP_TRANS_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_ESP_TRANS_LEVEL)");
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_ESP_TRANS_LEVEL,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "setsockopt(IPV6_ESP_TRANS_LEVEL)");
|
||||
}
|
||||
@ -825,7 +852,7 @@ main(int argc, char *argv[])
|
||||
} else {
|
||||
ICMP6_FILTER_SETPASSALL(&filt);
|
||||
}
|
||||
if (setsockopt(s, IPPROTO_ICMPV6, ICMP6_FILTER, &filt,
|
||||
if (setsockopt(srecv, IPPROTO_ICMPV6, ICMP6_FILTER, &filt,
|
||||
sizeof(filt)) < 0)
|
||||
err(1, "setsockopt(ICMP6_FILTER)");
|
||||
}
|
||||
@ -836,11 +863,11 @@ main(int argc, char *argv[])
|
||||
int opton = 1;
|
||||
|
||||
#ifdef IPV6_RECVRTHDR
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVRTHDR, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVRTHDR, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_RECVRTHDR)");
|
||||
#else /* old adv. API */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RTHDR, &opton,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RTHDR, &opton,
|
||||
sizeof(opton)))
|
||||
err(1, "setsockopt(IPV6_RTHDR)");
|
||||
#endif
|
||||
@ -849,7 +876,7 @@ main(int argc, char *argv[])
|
||||
/*
|
||||
optval = 1;
|
||||
if (IN6_IS_ADDR_MULTICAST(&dst.sin6_addr))
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_MULTICAST_LOOP,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_MULTICAST_LOOP,
|
||||
&optval, sizeof(optval)) == -1)
|
||||
err(1, "IPV6_MULTICAST_LOOP");
|
||||
*/
|
||||
@ -916,7 +943,7 @@ main(int argc, char *argv[])
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_family = AF_INET6;
|
||||
|
||||
if ((error = getaddrinfo(argv[hops], NULL, &hints,
|
||||
if ((error = cap_getaddrinfo(capdns, argv[hops], NULL, &hints,
|
||||
&res)))
|
||||
errx(1, "%s", gai_strerror(error));
|
||||
if (res->ai_addr->sa_family != AF_INET6)
|
||||
@ -931,6 +958,15 @@ main(int argc, char *argv[])
|
||||
scmsgp = CMSG_NXTHDR(&smsghdr, scmsgp);
|
||||
}
|
||||
|
||||
/* From now on we will use only reverse DNS lookups. */
|
||||
if (capdns != NULL) {
|
||||
const char *types[1];
|
||||
|
||||
types[0] = "ADDR2NAME";
|
||||
if (cap_dns_type_limit(capdns, types, nitems(types)) < 0)
|
||||
err(1, "unable to limit access to system.dns service");
|
||||
}
|
||||
|
||||
if (!(options & F_SRCADDR)) {
|
||||
/*
|
||||
* get the source address. XXX since we revoked the root
|
||||
@ -976,14 +1012,36 @@ main(int argc, char *argv[])
|
||||
close(dummy);
|
||||
}
|
||||
|
||||
if (connect(ssend, (struct sockaddr *)&dst, sizeof(dst)) != 0)
|
||||
err(1, "connect() ssend");
|
||||
|
||||
caph_cache_catpages();
|
||||
if (caph_enter_casper() < 0)
|
||||
err(1, "caph_enter_casper");
|
||||
|
||||
cap_rights_init(&rights_stdin);
|
||||
if (cap_rights_limit(STDIN_FILENO, &rights_stdin) < 0)
|
||||
err(1, "cap_rights_limit stdin");
|
||||
if (caph_limit_stdout() < 0)
|
||||
err(1, "caph_limit_stdout");
|
||||
if (caph_limit_stderr() < 0)
|
||||
err(1, "caph_limit_stderr");
|
||||
|
||||
cap_rights_init(&rights_srecv, CAP_RECV, CAP_EVENT, CAP_SETSOCKOPT);
|
||||
if (caph_rights_limit(srecv, &rights_srecv) < 0)
|
||||
err(1, "cap_rights_limit srecv");
|
||||
cap_rights_init(&rights_ssend, CAP_SEND, CAP_SETSOCKOPT);
|
||||
if (caph_rights_limit(ssend, &rights_ssend) < 0)
|
||||
err(1, "cap_rights_limit ssend");
|
||||
|
||||
#if defined(SO_SNDBUF) && defined(SO_RCVBUF)
|
||||
if (sockbufsize) {
|
||||
if (datalen > (size_t)sockbufsize)
|
||||
warnx("you need -b to increase socket buffer size");
|
||||
if (setsockopt(s, SOL_SOCKET, SO_SNDBUF, &sockbufsize,
|
||||
if (setsockopt(ssend, SOL_SOCKET, SO_SNDBUF, &sockbufsize,
|
||||
sizeof(sockbufsize)) < 0)
|
||||
err(1, "setsockopt(SO_SNDBUF)");
|
||||
if (setsockopt(s, SOL_SOCKET, SO_RCVBUF, &sockbufsize,
|
||||
if (setsockopt(srecv, SOL_SOCKET, SO_RCVBUF, &sockbufsize,
|
||||
sizeof(sockbufsize)) < 0)
|
||||
err(1, "setsockopt(SO_RCVBUF)");
|
||||
}
|
||||
@ -997,7 +1055,7 @@ main(int argc, char *argv[])
|
||||
* to get some stuff for /etc/ethers.
|
||||
*/
|
||||
hold = 48 * 1024;
|
||||
setsockopt(s, SOL_SOCKET, SO_RCVBUF, (char *)&hold,
|
||||
setsockopt(srecv, SOL_SOCKET, SO_RCVBUF, (char *)&hold,
|
||||
sizeof(hold));
|
||||
}
|
||||
#endif
|
||||
@ -1005,25 +1063,32 @@ main(int argc, char *argv[])
|
||||
optval = 1;
|
||||
#ifndef USE_SIN6_SCOPE_ID
|
||||
#ifdef IPV6_RECVPKTINFO
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVPKTINFO, &optval,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVPKTINFO, &optval,
|
||||
sizeof(optval)) < 0)
|
||||
warn("setsockopt(IPV6_RECVPKTINFO)"); /* XXX err? */
|
||||
#else /* old adv. API */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_PKTINFO, &optval,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_PKTINFO, &optval,
|
||||
sizeof(optval)) < 0)
|
||||
warn("setsockopt(IPV6_PKTINFO)"); /* XXX err? */
|
||||
#endif
|
||||
#endif /* USE_SIN6_SCOPE_ID */
|
||||
#ifdef IPV6_RECVHOPLIMIT
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_RECVHOPLIMIT, &optval,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_RECVHOPLIMIT, &optval,
|
||||
sizeof(optval)) < 0)
|
||||
warn("setsockopt(IPV6_RECVHOPLIMIT)"); /* XXX err? */
|
||||
#else /* old adv. API */
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_HOPLIMIT, &optval,
|
||||
if (setsockopt(srecv, IPPROTO_IPV6, IPV6_HOPLIMIT, &optval,
|
||||
sizeof(optval)) < 0)
|
||||
warn("setsockopt(IPV6_HOPLIMIT)"); /* XXX err? */
|
||||
#endif
|
||||
|
||||
cap_rights_clear(&rights_srecv, CAP_SETSOCKOPT);
|
||||
if (caph_rights_limit(srecv, &rights_srecv) < 0)
|
||||
err(1, "cap_rights_limit srecv setsockopt");
|
||||
cap_rights_clear(&rights_ssend, CAP_SETSOCKOPT);
|
||||
if (caph_rights_limit(ssend, &rights_ssend) < 0)
|
||||
err(1, "cap_rights_limit ssend setsockopt");
|
||||
|
||||
printf("PING6(%lu=40+8+%lu bytes) ", (unsigned long)(40 + pingerlen()),
|
||||
(unsigned long)(pingerlen() - 8));
|
||||
printf("%s --> ", pr_addr((struct sockaddr *)&src, sizeof(src)));
|
||||
@ -1081,7 +1146,7 @@ main(int argc, char *argv[])
|
||||
}
|
||||
#endif
|
||||
FD_ZERO(&rfds);
|
||||
FD_SET(s, &rfds);
|
||||
FD_SET(srecv, &rfds);
|
||||
gettimeofday(&now, NULL);
|
||||
timeout.tv_sec = last.tv_sec + intvl.tv_sec - now.tv_sec;
|
||||
timeout.tv_usec = last.tv_usec + intvl.tv_usec - now.tv_usec;
|
||||
@ -1096,7 +1161,7 @@ main(int argc, char *argv[])
|
||||
if (timeout.tv_sec < 0)
|
||||
timeout.tv_sec = timeout.tv_usec = 0;
|
||||
|
||||
n = select(s + 1, &rfds, NULL, NULL, &timeout);
|
||||
n = select(srecv + 1, &rfds, NULL, NULL, &timeout);
|
||||
if (n < 0)
|
||||
continue; /* EINTR */
|
||||
if (n == 1) {
|
||||
@ -1111,7 +1176,7 @@ main(int argc, char *argv[])
|
||||
m.msg_control = (void *)cm;
|
||||
m.msg_controllen = CONTROLLEN;
|
||||
|
||||
cc = recvmsg(s, &m, 0);
|
||||
cc = recvmsg(srecv, &m, 0);
|
||||
if (cc < 0) {
|
||||
if (errno != EINTR) {
|
||||
warn("recvmsg");
|
||||
@ -1325,15 +1390,13 @@ pinger(void)
|
||||
errx(1, "internal error; length mismatch");
|
||||
#endif
|
||||
|
||||
smsghdr.msg_name = (caddr_t)&dst;
|
||||
smsghdr.msg_namelen = sizeof(dst);
|
||||
memset(&iov, 0, sizeof(iov));
|
||||
iov[0].iov_base = (caddr_t)outpack;
|
||||
iov[0].iov_len = cc;
|
||||
smsghdr.msg_iov = iov;
|
||||
smsghdr.msg_iovlen = 1;
|
||||
|
||||
i = sendmsg(s, &smsghdr, 0);
|
||||
i = sendmsg(ssend, &smsghdr, 0);
|
||||
|
||||
if (i < 0 || i != cc) {
|
||||
if (i < 0)
|
||||
@ -2497,7 +2560,8 @@ pr_addr(struct sockaddr *addr, int addrlen)
|
||||
if ((options & F_HOSTNAME) == 0)
|
||||
flag |= NI_NUMERICHOST;
|
||||
|
||||
if (getnameinfo(addr, addrlen, buf, sizeof(buf), NULL, 0, flag) == 0)
|
||||
if (cap_getnameinfo(capdns, addr, addrlen, buf, sizeof(buf), NULL, 0,
|
||||
flag) == 0)
|
||||
return (buf);
|
||||
else
|
||||
return "?";
|
||||
@ -2631,7 +2695,7 @@ setpolicy(int so __unused, char *policy)
|
||||
buf = ipsec_set_policy(policy, strlen(policy));
|
||||
if (buf == NULL)
|
||||
errx(1, "%s", ipsec_strerror());
|
||||
if (setsockopt(s, IPPROTO_IPV6, IPV6_IPSEC_POLICY, buf,
|
||||
if (setsockopt(ssend, IPPROTO_IPV6, IPV6_IPSEC_POLICY, buf,
|
||||
ipsec_get_policylen(buf)) < 0)
|
||||
warnx("Unable to set IPsec policy");
|
||||
free(buf);
|
||||
@ -2728,3 +2792,29 @@ usage(void)
|
||||
" [-X timeout] [hops ...] host\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
static cap_channel_t *
|
||||
capdns_setup(void)
|
||||
{
|
||||
cap_channel_t *capcas, *capdnsloc;
|
||||
const char *types[2];
|
||||
int families[1];
|
||||
|
||||
capcas = cap_init();
|
||||
if (capcas == NULL)
|
||||
err(1, "unable to create casper process");
|
||||
capdnsloc = cap_service_open(capcas, "system.dns");
|
||||
/* Casper capability no longer needed. */
|
||||
cap_close(capcas);
|
||||
if (capdnsloc == NULL)
|
||||
err(1, "unable to open system.dns service");
|
||||
types[0] = "NAME2ADDR";
|
||||
types[1] = "ADDR2NAME";
|
||||
if (cap_dns_type_limit(capdnsloc, types, nitems(types)) < 0)
|
||||
err(1, "unable to limit access to system.dns service");
|
||||
families[0] = AF_INET6;
|
||||
if (cap_dns_family_limit(capdnsloc, families, nitems(families)) < 0)
|
||||
err(1, "unable to limit access to system.dns service");
|
||||
|
||||
return (capdnsloc);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user