I've been doing a lot of VPN related stuff lately, and today I figured out how to run dnscrypt-proxy on a vpn server, and route all client dns queries through dnscrypt. It is a wonderful, but irritating program to install. I thought I'd share my configurations here, to help others, but also so that next time I have to do this I will have a reference.
First, install dnscrypt-proxy. If you are running something Debian based on the server, this auto-install script is great. (If you're on another system, or don't trust that code, grab it from the main site.) However, I did have to create the init scripts and configuration files myself. Never fear, the instructions are here.
First, install dnscrypt-proxy and unbound. I used this debian auto-installer I found on github.
git clone https://github.com/simonclausen/dnscrypt-autoinstall
chmod +x dnscrypt-autoinstall.sh
./dnscrypt-autoinstall.sh && sudo apt-get install unbound
Edit: If the compiler is complaining about a syntax error....
checking whether to enable maintainer-specific portions of Makefiles... no
./configure: line 3264: syntax error near unexpected token `SYSTEMD,'
./configure: line 3264: ` PKG_CHECK_MODULES(SYSTEMD, libsystemd, have_systemd=yes,'
Than try my dirty hack.
Now let's configure unbound. Unbound will act as our dns-cache, and also our dns server for the
local VPN network.
cd /etc/unbound
vi unbound.conf
Edit your configuration so that unbound is listening on the VPN server IP address, as well as the localhost.
# Unbound configuration file for Debian.
#
# See the unbound.conf(5) man page.
#
# See /usr/share/doc/unbound/examples/unbound.conf for a commented
# reference config file.
server:
# The following line will configure unbound to perform cryptographic
# DNSSEC validation using the root trust anchor.
auto-trust-anchor-file: "/var/lib/unbound/root.key"
server:
# access-control: 10.8.0.0/24 allow
logfile: "/var/log/unbound.log"
log-time-ascii: yes
module-config: "iterator"
do-not-query-localhost: no
interface: 127.0.0.1
interface: 10.8.0.1
access-control: 127.0.0.1 allow
access-control: 10.8.0.1/24 allow
forward-zone:
name: "."
forward-addr: 127.0.0.1@40
forward-first: no
remote-control:
control-enable: no
Check to make sure that dnscrypt has it's own user:
cat /etc/shadow | grep dnscrypt
dnscrypt:!:16516:0:99999:7:::
If not, add one:
adduser --system --home /run/dnscrypt --shell /bin/false --group --disabled-password --disabled-login dnscrypt |
Next, let's try to start dnscrypt-proxy. You may get a variety of errors, which we will fix. If it's already running, close it. Depending on your installation, you may have a configuration file in
/etc/default/dnscrypt-proxy
If not, (as was the case on my debian server), we will simply create an init script with the desired settings. Dnscrypt is random with it's installs. Try starting it up:
service dnscrypt-proxy start
sudo netstat -taupean | grep dnscrypt
If you see dnscrypt running in the netstat output, great. Now just edit the /etc/default/dnscrypt-proxy config file so that it is listening on a port other than 53, as not to conflict with our caching service, Unbound (port 40 in this example). If you get an error, proceed to the next step:
cd /etc/init.d
vi dnscrypt
And paste in this script:
#! /bin/sh
### BEGIN INIT INFO
# Provides: dnscrypt-proxy
# Required-Start: $local_fs $network
# Required-Stop: $local_fs
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
# Short-Description: dnscrypt-proxy
# Description: dnscrypt-proxy secure DNS client
### END INIT INFO
# Author: Simon Clausen <kontakt@simonclausen.dk>
# Edited by Chev Y.
PATH=/usr/sbin:/usr/bin:/sbin:/bin
DAEMON=/usr/local/sbin/dnscrypt-proxy
NAME=dnscrypt-proxy
case "$1" in
start)
echo "Starting $NAME"
#Edit: In most situations, this simple line of code will do the trick:
$DAEMON --daemonize --user=dnscrypt --local-address=127.0.0.1:40 -R opendns
#I had to do this the first time though:
# /usr/local/sbin/dnscrypt-proxy --local-address=127.0.0.1:40 --edns-payload-size=4096
# --pidfile=/run/dnscrypt/dnscrypt-proxy.pid --logfile=/var/log/dnscrypt-proxy.log
# --user=dnscrypt -R opendns --daemonize
;;
stop)
echo "Stopping $NAME"
pkill -f $DAEMON
;;
restart)
$0 stop
$0 start
;;
*)
echo "Usage: /etc/init.d/dnscrypt-proxy {start|stop|restart}"
exit 1
;;
esac
###End Init script
Remember, you may already have an init script in that directory. If so, skip that step.
You can choose a different name server to use, after the -R flag. There is a list of them here: https://github.com/jedisct1/dnscrypt-proxy/blob/master/dnscrypt-resolvers.csv
Now update the settings:
update-rc.d dnscrypt-proxy defaults
Restart Unbound and Start Dnscrypt:
sudo service unbound restart && sudo service dnscrypt start
Update your /etc/resolv.conf file to that it reads
nameserver 127.0.0.1
Set iptables so that the vpn network may access unbound:
iptables -A INPUT -s 10.8.0.0/24 -p tcp -m tcp --dport 53 -j ACCEPT
iptables -A INPUT -s 10.8.0.0/24 -p udp -m udp --dport 53 -j ACCEPT
And finally, edit either your server.conf or ccd/client file(s) so that DNS is served by the VPN server:
push "dhcp-option DNS 10.8.0.1"
Make sure that worked. From a client, run:
dig @10.8.0.1 google.com
And check that the query was answered by the nameserver you selected for dnscrypt to use. Note: if you continue to have trouble starting dnscrypt, check that directory /run/dnscrypt is owned by the user dnscrypt:
ls -la /run/dnscrypt
In some cases user dnscrypt must own this directory or the program won't start.
That's it. Congraduations, your VPN server and all it's client's DNS queries are now fully encrypted! Kiss cache poisoning goodbye.
No comments:
Post a Comment