DNS Tunneling with iodine

27 Mar 2013

In this post we will be discussing the DNS protocol and how to tunnel traffic over DNS. DNS is a protocol which is considered relatively harmless as a result a lot of access points and firewalls allow DNS traffic without blinking once, this makes it ideal to use when you need to tunnel traffic. We will specifically be exploring a tool specifically made tunneling over DNS called 'iodine'.

Refreshing DNS

How does DNS work? DNS is the Domain Name System is allows us to translate easily memorized names to a numerical IP which the computer understands. To facilitate this service there are a few known servers called 'root servers' who are at the top of the DNS hierarchy, there are currently 13 root servers. These root servers know the authorative name server for the top-domains (.com, .eu, .nl, .be, .net). An authorative name server is responsible for one or more (sub)domains. When someone purchases a domain name, it's considered a subdomain of the top domain and as said, every subdomain can have it's own authorative nameserver. For instance if you have example.com, example is actually a subdomain of .com, the IPs for example.com are configured on another name server than the one who is responsible for example.com, we call this the authorative name server for example.com. Now example.com can have another subdomain which can also have its own subdomain, for instance, www.example.com, but also test.example.com and so on. Do not that not every subdomain has its own authorative name server, one server can be responsible for multiple domains. The design is hierarchical:


Normally a computer has a DNS server configured, reachable from its network, to which it can ask to resolve an IP (recursive name server). If the recursive name server doesn't know the IP, it will ask another DNS server. So to resolve a name to an IP this is happening

  • Computer: I need to know the IP of example.com, I shall query the configured DNS server A
  • DNS server A: Computer needs to resolve example.com, I don't know example.com, but I know who knows .com, I'll ask DNS Server B
  • DNS server B: I don't know the IP of example.com, but I know the server who is responsible for example.com, it's DNS Server C
  • DNS server A: Hello DNS server C, what is the IP of example.com?
  • DNS server C: Hello DNS server A, I know the IP for example.com, it's
  • DNS server A: Hello computer, the IP address of example.com is
This is a rather simplistic explanation, if you are not familiar at all with DNS I refer you to Understanding how DNS works .

What is DNS Tunneling?

As mentioned before, often firewalls and wireless access points will allow DNS traffic to pass without blinking twice. This is what DNS tunneling will exploit, it will encapsulate its traffic into a DNS request and forward it to a special DNS server which understands that the request is actually traffic and not a normal DNS request. So this means you can connect point-to-point with a server under your control. From here you can perform an SSH connection and create an additional SOCKS5 proxy tunnel. You can then tunnel all your TCP traffic through the SOCKS5 proxy. Below you can find a depiction which shows this concept in a schematic form:

Image from infosecinstitute.com


Iodine is a piece of software that allows us to set up DNS tunnels:

iodine lets you tunnel IPv4 data through a DNS server. This can be usable in different situations where internet access is firewalled, but DNS queries are allowed. It runs on Linux, Mac OS X, FreeBSD, NetBSD, OpenBSD and Windows and needs a TUN/TAP device. The bandwidth is asymmetrical with limited upstream and up to 1 Mbit/s downstream.
So what do you need?
  • a server under your control with a static IP address
  • a domain (we will use example.com) from which you can delegate a subdomain
  • iodine
I'm using Backtrack for both endpoints. For your domain create an additional subdomain, let's say tunnel.example.com. Create an A record and point it to your static IP address, also create an NS record, let's say route53.tunnel.example.com and point it to tunnel.example.com. You need an IP range which is not in use on your network as this will be used for your point-to-point tunnel, I used . On the server run the following launch iodined:

./iodined -fP MySuperSecretP4ssw0rd route53.tunnel.example.com

On the client:

./iodine -fP MySuperSecretP4ssw0rd route53.tunnel.example.com
  • -f Keep running in the foreground
  • -P password

Your client will then get an IP assigned on a new interface, execute the command:


You should so an interface called dnsX (where X is a number). The IP for that entry is your client's IP. Now you can connect to the IP of your server ( SSH and set up a proxy:

ssh [email protected] -D 5555
  • -D [bind address:port] (this is where our SOCKS5 proxy will listen on, if you only give a portnumber it will listen on localhost on the given port number)

Most applications support SOCKS5 tunneling and otherwise I would like to refer you to one of my previous posts. So now you know how you can circumvent network restrictions and use DNS to create a covert channel.