summaryrefslogtreecommitdiffstats
path: root/contrib/tcpdump
diff options
context:
space:
mode:
authorpjd <pjd@FreeBSD.org>2013-12-15 23:02:36 +0000
committerpjd <pjd@FreeBSD.org>2013-12-15 23:02:36 +0000
commit457e0637b9cdfb9176bb3a368f5465c2fbe03f8f (patch)
treea0452c0927a90f3988e817a5f9f94965efa2f17c /contrib/tcpdump
parent6aa4815cf61baa9edf7ef2b81c5f53c358d5b4f1 (diff)
downloadFreeBSD-src-457e0637b9cdfb9176bb3a368f5465c2fbe03f8f.zip
FreeBSD-src-457e0637b9cdfb9176bb3a368f5465c2fbe03f8f.tar.gz
Make use of casperd's system.dns service when running without the -n option.
Now tcpdump(8) is sandboxed even if DNS resolution is required. Sponsored by: The FreeBSD Foundation
Diffstat (limited to 'contrib/tcpdump')
-rw-r--r--contrib/tcpdump/addrtoname.c23
-rw-r--r--contrib/tcpdump/tcpdump.c62
2 files changed, 82 insertions, 3 deletions
diff --git a/contrib/tcpdump/addrtoname.c b/contrib/tcpdump/addrtoname.c
index 10ec7db..3b0d65c 100644
--- a/contrib/tcpdump/addrtoname.c
+++ b/contrib/tcpdump/addrtoname.c
@@ -32,6 +32,10 @@ static const char rcsid[] _U_ =
#include "config.h"
#endif
+#ifdef __FreeBSD__
+#include <libcapsicum.h>
+#include <libcapsicum_dns.h>
+#endif
#include <tcpdump-stdinc.h>
#ifdef USE_ETHER_NTOHOST
@@ -203,6 +207,9 @@ intoa(u_int32_t addr)
static u_int32_t f_netmask;
static u_int32_t f_localnet;
+#ifdef HAVE_LIBCAPSICUM
+extern cap_channel_t *capdns;
+#endif
/*
* Return a name for the IP address pointed to by ap. This address
@@ -248,7 +255,13 @@ getname(const u_char *ap)
*/
if (!nflag &&
(addr & f_netmask) == f_localnet) {
- hp = gethostbyaddr((char *)&addr, 4, AF_INET);
+#ifdef HAVE_LIBCAPSICUM
+ if (capdns != NULL) {
+ hp = cap_gethostbyaddr(capdns, (char *)&addr, 4,
+ AF_INET);
+ } else
+#endif
+ hp = gethostbyaddr((char *)&addr, 4, AF_INET);
if (hp) {
char *dotp;
@@ -293,7 +306,13 @@ getname6(const u_char *ap)
* Do not print names if -n was given.
*/
if (!nflag) {
- hp = gethostbyaddr((char *)&addr, sizeof(addr), AF_INET6);
+#ifdef HAVE_LIBCAPSICUM
+ if (capdns != NULL) {
+ hp = cap_gethostbyaddr(capdns, (char *)&addr,
+ sizeof(addr), AF_INET6);
+ } else
+#endif
+ hp = gethostbyaddr((char *)&addr, sizeof(addr), AF_INET6);
if (hp) {
char *dotp;
diff --git a/contrib/tcpdump/tcpdump.c b/contrib/tcpdump/tcpdump.c
index afcc152..e1a34f4 100644
--- a/contrib/tcpdump/tcpdump.c
+++ b/contrib/tcpdump/tcpdump.c
@@ -76,6 +76,12 @@ extern int SIZE_BUF;
#include <net/bpf.h>
#include <fcntl.h>
#include <libgen.h>
+#ifdef HAVE_LIBCAPSICUM
+#include <libcapsicum.h>
+#include <libcapsicum_dns.h>
+#include <libcapsicum_service.h>
+#include <nv.h>
+#endif /* HAVE_LIBCAPSICUM */
#endif /* __FreeBSD__ */
#ifndef WIN32
#include <sys/wait.h>
@@ -123,6 +129,10 @@ static int infoprint;
char *program_name;
+#ifdef HAVE_LIBCAPSICUM
+cap_channel_t *capdns;
+#endif
+
int32_t thiszone; /* seconds offset from gmt to local time */
/* Forwards */
@@ -684,6 +694,45 @@ get_next_file(FILE *VFile, char *ptr)
return ret;
}
+#ifdef HAVE_LIBCAPSICUM
+static cap_channel_t *
+capdns_setup(void)
+{
+ cap_channel_t *capcas, *capdnsloc;
+ const char *types[1];
+ int families[2];
+
+ capcas = cap_init();
+ if (capcas == NULL) {
+ warning("unable to contact casperd");
+ return (NULL);
+ }
+ capdnsloc = cap_service_open(capcas, "system.dns");
+ /* Casper capability no longer needed. */
+ cap_close(capcas);
+ if (capdnsloc == NULL) {
+ warning("unable to open system.dns service");
+ return (NULL);
+ }
+ /* Limit system.dns to reverse DNS lookups. */
+ types[0] = "ADDR";
+ if (cap_dns_type_limit(capdnsloc, types, 1) < 0) {
+ warning("unable to limit access to system.dns service");
+ cap_close(capdnsloc);
+ return (NULL);
+ }
+ families[0] = AF_INET;
+ families[1] = AF_INET6;
+ if (cap_dns_family_limit(capdnsloc, families, 2) < 0) {
+ warning("unable to limit access to system.dns service");
+ cap_close(capdnsloc);
+ return (NULL);
+ }
+
+ return (capdnsloc);
+}
+#endif /* HAVE_LIBCAPSICUM */
+
int
main(int argc, char **argv)
{
@@ -1417,6 +1466,12 @@ main(int argc, char **argv)
free(cmdbuf);
exit(0);
}
+
+#ifdef HAVE_LIBCAPSICUM
+ if (!nflag)
+ capdns = capdns_setup();
+#endif /* HAVE_LIBCAPSICUM */
+
init_addrtoname(localnet, netmask);
init_checksum();
@@ -1615,7 +1670,12 @@ main(int argc, char **argv)
#endif /* WIN32 */
#ifdef __FreeBSD__
- cansandbox = (nflag && VFileName == NULL && zflag == NULL);
+ cansandbox = (VFileName == NULL && zflag == NULL);
+#ifdef HAVE_LIBCAPSICUM
+ cansandbox = (cansandbox && (nflag || capdns != NULL));
+#else
+ cansandbox = (cansandbox && nflag);
+#endif
if (cansandbox && cap_enter() < 0 && errno != ENOSYS)
error("unable to enter the capability mode");
if (cap_sandboxed())
OpenPOWER on IntegriCloud