[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[GNUnet-SVN] r38037 - in gnunet/src: dns include tun
From: |
gnunet |
Subject: |
[GNUnet-SVN] r38037 - in gnunet/src: dns include tun |
Date: |
Wed, 28 Sep 2016 00:25:06 +0200 |
Author: grothoff
Date: 2016-09-28 00:25:05 +0200 (Wed, 28 Sep 2016)
New Revision: 38037
Modified:
gnunet/src/dns/Makefile.am
gnunet/src/dns/dnsstub.c
gnunet/src/dns/gnunet-helper-dns.c
gnunet/src/dns/gnunet-service-dns.c
gnunet/src/dns/test_gnunet_dns.sh
gnunet/src/include/gnunet_tun_lib.h
gnunet/src/tun/tun.c
Log:
fixes relating to intercepting DNS queries over IPv6
Modified: gnunet/src/dns/Makefile.am
===================================================================
--- gnunet/src/dns/Makefile.am 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/dns/Makefile.am 2016-09-27 22:25:05 UTC (rev 38037)
@@ -89,6 +89,7 @@
libgnunetdnsstub_la_SOURCES = \
dnsstub.c
libgnunetdnsstub_la_LIBADD = \
+ $(top_builddir)/src/tun/libgnunettun.la \
$(top_builddir)/src/util/libgnunetutil.la $(XLIB)
libgnunetdnsstub_la_LDFLAGS = \
$(GN_LIB_LDFLAGS) \
Modified: gnunet/src/dns/dnsstub.c
===================================================================
--- gnunet/src/dns/dnsstub.c 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/dns/dnsstub.c 2016-09-27 22:25:05 UTC (rev 38037)
@@ -24,6 +24,7 @@
*/
#include "platform.h"
#include "gnunet_util_lib.h"
+#include "gnunet_tun_lib.h"
#include "gnunet_dnsstub_lib.h"
/**
@@ -381,9 +382,7 @@
_("Failed to send DNS request to %s\n"),
GNUNET_a2s (sa, salen));
rs->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT);
-
return rs;
-
}
@@ -441,9 +440,10 @@
}
dns = (struct GNUNET_TUN_DnsHeader *) buf;
if ( (addrlen != rs->addrlen) ||
- (0 != memcmp (&rs->addr,
- &addr,
- addrlen)) ||
+ (GNUNET_YES !=
+ GNUNET_TUN_sockaddr_cmp ((struct sockaddr *) &rs->addr,
+ (struct sockaddr *) &addr,
+ GNUNET_YES)) ||
(0 == GNUNET_TIME_absolute_get_remaining (rs->timeout).rel_value_us) )
{
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
Modified: gnunet/src/dns/gnunet-helper-dns.c
===================================================================
--- gnunet/src/dns/gnunet-helper-dns.c 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/dns/gnunet-helper-dns.c 2016-09-27 22:25:05 UTC (rev 38037)
@@ -101,6 +101,11 @@
static const char *sbin_iptables;
/**
+ * Name and full path of IPTABLES binary.
+ */
+static const char *sbin_ip6tables;
+
+/**
* Name and full path of sysctl binary
*/
static const char *sbin_sysctl;
@@ -757,7 +762,7 @@
return 254;
}
#endif
- if (0 == strncmp(argv[6], "1", 2))
+ if (0 == strncmp (argv[6], "1", 2))
nortsetup = 1;
if (0 == nortsetup)
@@ -774,6 +779,17 @@
strerror (errno));
return 3;
}
+ if (0 == access ("/sbin/ip6tables", X_OK))
+ sbin_ip6tables = "/sbin/ip6tables";
+ else if (0 == access ("/usr/sbin/ip6tables", X_OK))
+ sbin_ip6tables = "/usr/sbin/ip6tables";
+ else
+ {
+ fprintf (stderr,
+ "Fatal: executable ip6tables not found in approved directories:
%s\n",
+ strerror (errno));
+ return 3;
+ }
if (0 == access ("/sbin/ip", X_OK))
sbin_ip = "/sbin/ip";
else if (0 == access ("/usr/sbin/ip", X_OK))
@@ -942,6 +958,16 @@
if (0 != fork_and_exec (sbin_iptables, mangle_args))
goto cleanup_rest;
}
+ {
+ char *const mangle_args[] =
+ {
+ "ip6tables", "-m", "owner", "-t", "mangle", "-I", "OUTPUT", "1", "-p",
+ "udp", "--gid-owner", mygid, "--dport", DNS_PORT, "-j",
+ "ACCEPT", NULL
+ };
+ if (0 != fork_and_exec (sbin_ip6tables, mangle_args))
+ goto cleanup_rest;
+ }
/* Mark all of the other DNS traffic using our mark DNS_MARK */
{
char *const mark_args[] =
@@ -953,6 +979,16 @@
if (0 != fork_and_exec (sbin_iptables, mark_args))
goto cleanup_mangle_1;
}
+ {
+ char *const mark_args[] =
+ {
+ "ip6tables", "-t", "mangle", "-I", "OUTPUT", "2", "-p",
+ "udp", "--dport", DNS_PORT, "-j", "MARK", "--set-mark", DNS_MARK,
+ NULL
+ };
+ if (0 != fork_and_exec (sbin_ip6tables, mark_args))
+ goto cleanup_mangle_1;
+ }
/* Forward all marked DNS traffic to our DNS_TABLE */
{
char *const forward_args[] =
@@ -962,6 +998,14 @@
if (0 != fork_and_exec (sbin_ip, forward_args))
goto cleanup_mark_2;
}
+ {
+ char *const forward_args[] =
+ {
+ "ip", "-6", "rule", "add", "fwmark", DNS_MARK, "table", DNS_TABLE,
NULL
+ };
+ if (0 != fork_and_exec (sbin_ip, forward_args))
+ goto cleanup_mark_2;
+ }
/* Finally, add rule in our forwarding table to pass to our virtual
interface */
{
char *const route_args[] =
@@ -972,6 +1016,15 @@
if (0 != fork_and_exec (sbin_ip, route_args))
goto cleanup_forward_3;
}
+ {
+ char *const route_args[] =
+ {
+ "ip", "-6", "route", "add", "default", "dev", dev,
+ "table", DNS_TABLE, NULL
+ };
+ if (0 != fork_and_exec (sbin_ip, route_args))
+ goto cleanup_forward_3;
+ }
}
/* drop privs *except* for the saved UID; this is not perfect, but better
@@ -1028,6 +1081,16 @@
if (0 != fork_and_exec (sbin_ip, route_clean_args))
r += 1;
}
+ if (0 == nortsetup)
+ {
+ char *const route_clean_args[] =
+ {
+ "ip", "-6", "route", "del", "default", "dev", dev,
+ "table", DNS_TABLE, NULL
+ };
+ if (0 != fork_and_exec (sbin_ip, route_clean_args))
+ r += 1;
+ }
cleanup_forward_3:
if (0 == nortsetup)
{
@@ -1038,6 +1101,15 @@
if (0 != fork_and_exec (sbin_ip, forward_clean_args))
r += 2;
}
+ if (0 == nortsetup)
+ {
+ char *const forward_clean_args[] =
+ {
+ "ip", "-6", "rule", "del", "fwmark", DNS_MARK, "table", DNS_TABLE, NULL
+ };
+ if (0 != fork_and_exec (sbin_ip, forward_clean_args))
+ r += 2;
+ }
cleanup_mark_2:
if (0 == nortsetup)
{
@@ -1049,6 +1121,16 @@
if (0 != fork_and_exec (sbin_iptables, mark_clean_args))
r += 4;
}
+ if (0 == nortsetup)
+ {
+ char *const mark_clean_args[] =
+ {
+ "ip6tables", "-t", "mangle", "-D", "OUTPUT", "-p", "udp",
+ "--dport", DNS_PORT, "-j", "MARK", "--set-mark", DNS_MARK, NULL
+ };
+ if (0 != fork_and_exec (sbin_ip6tables, mark_clean_args))
+ r += 4;
+ }
cleanup_mangle_1:
if (0 == nortsetup)
{
@@ -1061,6 +1143,17 @@
if (0 != fork_and_exec (sbin_iptables, mangle_clean_args))
r += 8;
}
+ if (0 == nortsetup)
+ {
+ char *const mangle_clean_args[] =
+ {
+ "ip6tables", "-m", "owner", "-t", "mangle", "-D", "OUTPUT", "-p", "udp",
+ "--gid-owner", mygid, "--dport", DNS_PORT, "-j", "ACCEPT",
+ NULL
+ };
+ if (0 != fork_and_exec (sbin_ip6tables, mangle_clean_args))
+ r += 8;
+ }
cleanup_rest:
/* close virtual interface */
Modified: gnunet/src/dns/gnunet-service-dns.c
===================================================================
--- gnunet/src/dns/gnunet-service-dns.c 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/dns/gnunet-service-dns.c 2016-09-27 22:25:05 UTC (rev 38037)
@@ -410,7 +410,7 @@
destination_port = src->sin6_port;
GNUNET_TUN_initialize_ipv6_header (&ip6,
IPPROTO_UDP,
- reply_len - sizeof (struct
GNUNET_TUN_IPv6Header),
+ reply_len - off - sizeof (struct
GNUNET_TUN_IPv6Header),
&dst->sin6_addr,
&src->sin6_addr);
GNUNET_memcpy (&buf[off], &ip6, sizeof (ip6));
@@ -916,7 +916,7 @@
ip6 = (const struct GNUNET_TUN_IPv6Header *) &tun[1];
if ( (msize < sizeof (struct GNUNET_TUN_IPv6Header)) ||
(ip6->version != 6) ||
- (ntohs (ip6->payload_length) != msize) ||
+ (ntohs (ip6->payload_length) != msize - sizeof (struct
GNUNET_TUN_IPv6Header)) ||
(ip6->next_header != IPPROTO_UDP) )
{
/* non-IP/UDP packet received on TUN (or with extensions) */
@@ -924,7 +924,7 @@
_("Received malformed IPv6-UDP packet on TUN interface.\n"));
return GNUNET_OK;
}
- udp = (const struct GNUNET_TUN_UdpHeader*) &ip6[1];
+ udp = (const struct GNUNET_TUN_UdpHeader *) &ip6[1];
msize -= sizeof (struct GNUNET_TUN_IPv6Header);
break;
default:
@@ -939,6 +939,8 @@
(DNS_PORT != ntohs (udp->destination_port)) )
{
/* non-DNS packet received on TUN, ignore */
+ GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
+ _("DNS interceptor got non-DNS packet (dropped)\n"));
GNUNET_STATISTICS_update (stats,
gettext_noop ("# Non-DNS UDP packet received via
TUN interface"),
1, GNUNET_NO);
Modified: gnunet/src/dns/test_gnunet_dns.sh
===================================================================
--- gnunet/src/dns/test_gnunet_dns.sh 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/dns/test_gnunet_dns.sh 2016-09-27 22:25:05 UTC (rev 38037)
@@ -6,7 +6,7 @@
echo "This test only works if run as root. Skipping."
exit 77
fi
-if ! which sudo > /dev/null
+if ! which sudo > /dev/null
then
echo "This test requires sudo. Skipping."
exit 77
@@ -17,7 +17,7 @@
exit 77
fi
if ! which nslookup > /dev/null
-then
+then
echo "This test requires nslookup. Skipping."
exit 77
fi
@@ -38,7 +38,7 @@
sleep 1
# need to run 'nslookup' as 'nobody', as gnunet-service-dns runs as root
# and thus 'root' is excepted from DNS interception!
-LO=`sudo -u nobody nslookup gnunet.org | grep Address | tail -n1`
+LO=`sudo -u nobody nslookup -type=A gnunet.org | grep Address | tail -n1`
if [ "$LO" != "Address: 127.0.0.1" ]
then
echo "Fail: got address $LO, wanted 127.0.0.1"
Modified: gnunet/src/include/gnunet_tun_lib.h
===================================================================
--- gnunet/src/include/gnunet_tun_lib.h 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/include/gnunet_tun_lib.h 2016-09-27 22:25:05 UTC (rev 38037)
@@ -918,6 +918,20 @@
/**
+ * Check if two sockaddrs are equal.
+ *
+ * @param sa one address
+ * @param sb another address
+ * @param include_port also check ports
+ * @return #GNUNET_YES if they are equal
+ */
+int
+GNUNET_TUN_sockaddr_cmp (const struct sockaddr *sa,
+ const struct sockaddr *sb,
+ int include_port);
+
+
+/**
* Compute the CADET port given a service descriptor
* (returned from #GNUNET_TUN_service_name_to_hash) and
* a TCP/UDP port @a ip_port.
Modified: gnunet/src/tun/tun.c
===================================================================
--- gnunet/src/tun/tun.c 2016-09-27 18:36:44 UTC (rev 38036)
+++ gnunet/src/tun/tun.c 2016-09-27 22:25:05 UTC (rev 38037)
@@ -70,7 +70,7 @@
*
* @param ip header to initialize
* @param protocol protocol to use (i.e. IPPROTO_UDP), technically
"next_header" for IPv6
- * @param payload_length number of bytes of payload that follow (excluding
IPv4 header)
+ * @param payload_length number of bytes of payload that follow (excluding
IPv6 header)
* @param src source IP address to use
* @param dst destination IP address to use
*/
@@ -268,4 +268,44 @@
}
+/**
+ * Check if two sockaddrs are equal.
+ *
+ * @param sa one address
+ * @param sb another address
+ * @param include_port also check ports
+ * @return #GNUNET_YES if they are equal
+ */
+int
+GNUNET_TUN_sockaddr_cmp (const struct sockaddr *sa,
+ const struct sockaddr *sb,
+ int include_port)
+{
+ if (sa->sa_family != sb->sa_family)
+ return GNUNET_NO;
+
+ switch (sa->sa_family)
+ {
+ case AF_INET:
+ {
+ const struct sockaddr_in *sa4 = (const struct sockaddr_in *) sa;
+ const struct sockaddr_in *sb4 = (const struct sockaddr_in *) sb;
+ return (sa4->sin_addr.s_addr == sb4->sin_addr.s_addr);
+ }
+ case AF_INET6:
+ {
+ const struct sockaddr_in6 *sa6 = (const struct sockaddr_in6 *) sa;
+ const struct sockaddr_in6 *sb6 = (const struct sockaddr_in6 *) sb;
+
+ return (0 == memcmp(&sa6->sin6_addr,
+ &sb6->sin6_addr,
+ sizeof (struct in6_addr)));
+ }
+ default:
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+}
+
+
/* end of tun.c */
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [GNUnet-SVN] r38037 - in gnunet/src: dns include tun,
gnunet <=