Mar 132011
 

Sometimes it is useful to have a DNS tunnel to circumvent too strict firewalls.

I already had installed and configured an iodine server on my AVM FRITZ!Box Fon WLAN 7270 v2 using Freetz and wanted to have an iodine client on my already rooted Sony Ericssons Xperia X10 mini. I started with looking for a suitable TUN Driver for my phone. Luckily I found one on the XDA developers forum. Next I started looking for a iodine client ported to Android. I found this one, but it didn’t work on my phone. So I decide to port iodine myself. This appeared to be not so simple, because the Android Linux is not a standard Linux. I had to change the source code on several places to make it work. I have sent a patch to the author of iodine, so maybe it will be part of the iodine package in the near future.

If you want to build iodine for Android yourself, you can follow these steps:

  • Download and install the Android SDK
  • Download and install the Android NDK
  • Download and unpack iodine-0.6.0-rc1
  • cd iodine-0.6.0-rc1/src
  • make base64u.h base64u.c
  • patch -p1 <…/iodine-0.6.0-rc1-android-3.patch
  • …/ndk-build NDK_PROJECT_PATH=. APP_BUILD_SCRIPT=Android.mk

If the compilation succeeded, you can now try the executable on your phone:

  • adb push ./libs/armeabi/iodine /data/local/tmp
  • adb shell
  • su
  • cd /data/local/tmp
  • chmod 777 iodine
  • ./iodine

It will not work from an SD card, because Android mounts SD cards non-executable!

I choose iodine over dns2tcp, because it is possible to route all traffic through the tunnel. To start the iodine client and to setup routing I created a shell script. If you want to use this script, you have to fill in your own server details. It depends on busybox provided by Titanium backup and it assumes that a tunnel will be created over WiFi (device wlan0).

To copy the TUN Driver and the startup script to your phone:

  • adb push tun.ko /data/local/tmp
  • adb push iodine.sh /data/local/tmp

You can now try to setup a DNS tunnel on your phone:

  • adb shell
  • su
  • cd /data/local/tmp/
  • chmod 777 iodine_route.sh
  • iodine_route.sh

I use Script Manager to start the tunnel from my phone.

You can restore the default routing by disabling and enabling WiFi.

If you want to store iodine on a permanent location, you can re-mount your system partition read-write:

  • mount -o remount,rw -t yaffs2 /dev/block/mtdblock<your block number> /system
  • ../busybox cp /data/local/tmp/* /system/xbin

Tip: my hosting provider didn’t allowed me to set NS records for a sub-domain, that is why I used the FreeDNS service.

Fun facts:

  • iod = IP over DNS
  • DNS port number = 53 = atomic number of iodine

Download the patch, script and generic binary.

Update 19/5/2012: even easier now: MagicTunnel.

Update 6/7/2012: see here for my own DNS tunnel implementation.

Comments and questions are as always very welcome.

  32 Responses to “iodine DNS tunnel for Android”

  1. my iodine doesnt route all connection through the tun/tap on my windows..someone got any script to start iodine on ubuntu 10.04 openvz server
    thanx

    • See here for routing.
      You can use something like this in /etc/rc.local to start iodine:

      mkdir -p /tmp/iodine
      /path/to/iodined -c -P secret -u nobody -t /tmp/iodine 10.0.0.1 t.example.com

  2. I have set up the server and it works when I connect from my laptop without any errors. All goes well.
    But when I connect from the android client by running iodine.sh, I get the following error in the iodined server console: “read dns: Result too large”. I can ping the server tunnel ip.

    • I have really no idea why you get this error, sorry.
      Maybe you can ask the author of iodine.

      • I will, thank you. Thing is everything works fine from the phone, but the error bugs me.

  3. Hi,

    great guide, followed it with success but, every time i start the binary my phone suddenly reboots. Tried compiling the binary myself but same results. The tun.ko is also compiled by me, loads without errors.
    I have a galaxy mini with 2.3.6.

    Any ideas on this issue?
    Thanks in advance
    zLaci


  4. iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
    iptables -t filter -A FORWARD -i eth0 -o dns0 -m state --state RELATED,ESTABLISHED -j ACCEPT
    iptables -t filter -A FORWARD -i dns0 -o eth0 -j ACCEPT

    VERY IMPORTANT ON THE SERVER SIDE

  5. Thanks, your precompiled binary and ipodns.sh work great on my SE MK16i (Android 2.3.4)! I downloaded tun.ko with “Tun.ko installer” from the Android market, a precompiled module was already available.

  6. Thank you very much!

    Now wifi at airports, hotels and at work are all free with phone and tab :)

    I use the app SSHTunnel to tunnel alle Traffic through the iodine tunnel. This is great, because I do not have to change the network settings by a script and it is completely encrypted.

  7. Hi, … I am looking for
    someone who helps me
    make a vpn or iodine as a VPN
    on Windows, my mail
    jgasserge@gmail. com … thank
    you

    • iodine on Windows is not simple to setup, because you will have to do the routing yourself, so concentrate on VPN. OpenVPN is simple to setup and well documented.

      Please note that your question is off-topic here (wrong operating system).
      This place is not intended for general support.

  8. Can i route android tcp53 to tcp 4453 by using your script?

    • This depends on if your (custom) firmware supports iptables, but it should be possible in most cases. Since all traffic is routed through the tunnel, you can also try to reroute the traffic that is coming out of the tunnel on your server.

    • My tunnel server is on a LAN. To prevent traffic between the tunnel and LAN I use the following iptables rules:

      -A INPUT -d 192.168.178.0/24 -i dns0 -j DROP 
      -A FORWARD -i dns0 -o dsl -j ACCEPT 
      -A FORWARD -i dns0 -j DROP 
      -A OUTPUT -s 192.168.178.0/24 -o dns0 -j DROP 
      -A PREROUTING -i tun0 -p tcp -m tcp --dport 53 -j DNAT --to-destination 192.168.178.1 
      -A PREROUTING -i tun0 -p udp -m udp --dport 53 -j DNAT --to-destination 192.168.178.1 
      

      Especially the last rules should give you an idea about how to solve this at the server side.

  9. Thanks for this guide!

    Everything seems to work fine for me, I can setup the tunnel, and access the server via the tunnel (via the 10.0.0.1 address that I chose, and ssh access works), but no other traffic works (such as regular web browsing, etc). I am assuming something is messed up in the traffic redirection?

    • Did you use the provided script? (download at the end of the post)

      • Thanks for the fast reply. Yeah, I was using the script at the end of the post. I just figured out the issue – I needed to setup iptables to masquerade the packets on the server.

  10. Thanks for sharing your iodine binary and patches.

    I installed it to my Android’ed HTC HD2 (came with Win Mobile 6.5, runs Cyanogenmod 7 now).

    Unfortunately, iodine does not bring up the “dns0″ device (but does not complain). The initialization process looks normal, but afterwards prints some special characters to the screen. It looks like the data which should be sent to “dns0″ is printed to the screen…

    I thought it might be related to the name “dns0″ and added “-d tun0″ to the shell script, to force the device being named “tun0″, but that doesn’t help.

    tun support is available (OpenVPN runs just fine). I start iodine via a shell script using the script manager you mentioned.

    Do you have any ideas on this?

    Kind regards, Sven

    • It is not iodine that makes the virtual device, this should be done by tun.ko. Maybe you didn’t insert this kernel module or maybe there is something wrong with your tun.ko.

  11. Hey I needed this thanks and what kind of speeds do u get?

  12. Oh wow, thats what i was looking for….Would you mind thinking about making android package or push this app to android market?

    • An Android application would be nice, but a lot of work. iodine has to be modified for it too.
      For me a script using a script manager is for the very few times I am gonna use iodine good enough.

  13. Hello, nice post. And thank you for providing all the details on how to compile.

    I have a G1 and i am using the iodine 0.5, i would like to try with 0.6. Could you please share the binary that you have compiled?

    Thank you very much,