So, just like a lot of other people, I am fighting my fight with adblocking. This post will not go into ethics of it, morality of it or what are alternatives – I might cover that with some other post. This time, I want to explain (what I think is) my ultimate setup for ad blocking! With it, you will get best adblocking experience wherever you are and on whatever device you are. This might not be best setup for you – it all depends how technical you want to get and how determine you are against ads. What you will get with this:

  • Blocking of most ads on all your devices
  • Blocking of most trackers on all your devices
  • This setup will save you data (really handy if you have limited data plan). Depending what site you visit, it can be up to 30% of your data (yes, I saw this).
  • This setup will secure all your communications (maybe not secure enough against government agencies, but good enough against unsecured wireless endpoints and your provider)
  • This setup will allow you to share it easily with others (friends don’t let friends watch ads)

What are downsides of this approach:

  • You need to have spare machine, with one UDP port open
  • Due to VPN use, all websites will see you as if you are coming from country where VPN is (it didn’t end up as a problem for me, but I have to point that out now)

My madness progression

This all started rather innocent (just like all horrid stuff do start) with simple ad-blocker in browser. BTW, if you want to stop reading, now is the time and I recommend Firefox browser with holy trinity of uBlock Origin, Privacy Badger and Decentraleyes – this should be good enough for all non-geek people.

But… this ad-blocker setup is not silver bullet, it will not save you from other forms of tracking, like ads inside applications or when generally application do phone home. So, as much as ads were getting smarter and smarter (if you like South Park, please do watch season 19 where this is analyzed much thoroughly), we also had to get smarter and smarter. My journey looked something like this:

I was satisfied with this setup until Viber once got rogue and slowed down my machine to the point it was unusable – ads were autoplaying, mouse was stuttering and there was no way to stop this. I even recorded that:

Viber ads go rogue (autoplaying, cannot stop it) from Branko Kokanovic on Vimeo.

So, that was last drop. Turns out, I was not the only one with this problem and searching internet, people were recommending to put “ads.viber.com” to hosts file, so that it points to 127.0.0.1. This way, any request going to ads.viber.com will be resolved to local address and effectively blocked. But you all knew that already. (Besides getting rid of Viber) I started toying around with /etc/hosts file, but that was not that pleasant experience and (from my experience) Windows is choking on large /etc/hosts file, so I wasn’t long on this setup. For the sake of completeness, here is excellent starting point to craft your own hosts file, if you are into that.

This is when I found out about Pi-hole – this is one of the best pieces of software ever created (not the idea, but whole execution). Pi-hole is complex software with simple idea – point your DNS to it and it will resolve all domains of ads and trackers as 127.0.0.1 and you will never even start a request with them. Installation and upgrade and usage – everything with it is just so smooth and everything “just works”. I don’t often donate money to free software, but in this case, I opened my wallet. And so I loaded Pi-hole to my Raspberry Pi and suddenly everyone in whole household (local LAN network) started benefiting from blocked ads and trackers. Life was good again. Except…when I was outside of home and it wasn’t.

This was unsolvable problem for me. Until I accidentally bumped to Streisand software that automates VPN setup with ansible recipes. And this awesome blog post that explains how to setup Streisand with Pi-hole. This is one beautiful idea – use VPN to always connect to local network wherever you are and put Pi-hole in that network and use it as your DNS resolver on-the-go. Not to mention benefits of VPN itself. I was sold! At the end, I didn’t use these advises (and rolled my own which are very similar) because:

  • I don’t know ansible
  • This is much more software than I asked for
  • I don’t like when complexity is huge (and I tend to try to understand what I am installing and why)
  • I already have VM and I didn’t know how to point ansible there and was afraid what horrible things will happen on my prod machine

That being said, if you want ultimate setup, please read mentioned blog, as it will use best practices, including WireGuard, socks5 and whatsnot, and will surely be more secure than my Frankenstein. Hack, even Pi-hole itself have nice explanation to integrate it in VPN. But if you just want to dip a toe and don’t care about world-class security, here is 5 minute guide (no, really, it is literally 5 minutes to set this up).

Steps to setup OpenVPN with Pi-hole

  • First you will need one machine with some newer Ubuntu (I have 18.04 LTS) – it can be any cloud VM or local machine, as long as you can open UDP port on it for whole world. This is port where VPN will listen. Any cloud provider will do, and any VM size will do. Do note that all your traffic will go through this machine, so check network pricing for your provider.

Alternatively, this can all be done in your home, on Raspberry Pi, but watch out your upload speed (mine is extremely slow), as your download speed while roaming will be bound by your upload speed at home. If you don’t want your traffic to go through this VM (or through your home), this is nice way to fix it, but this is outside of the scope of this tutorial.

  • SSH to that machine and install Pi-hole first (but it can done with installing OpenVPN first, doesn’t matter):
curl -sSL https://install.pi-hole.net | bash

Accept all default values, nothing special here. For upstream DNS providers, you can put Cloudflare’s 1.1.1.1 and 1.0.0.1, but you can also use Google ones – 8.8.8.8, or OpenDNS at 208.67.222.222.

  • Install OpenVPN (we are using here awesome PiVPN packaging):
 curl -L https://install.pivpn.io | bash

When asked for address of DNS server, provide “127.0.0.1” (this is where Pi-hole is). Second DNS can be either empty, or provide some existing one, I generally use “1.1.1.1”. You can accept all defaults for other values, nothing special here.

  • Change interface on which Pi-hole works and restart it

Installation of OpenVPN gave us new interface (it should be named “tun0”). Check new interface you see with ifconfig command. You should also get address that VPN is set up with command:

ifconfig tun0 | grep "inet " | awk '{print $2}'

For me, it is 10.8.0.1. This is interface and address we want Pi-hole to listen on. Open up “/etc/pihole/setupVars.conf” with your favorite editor and make sure those two lines looks like this:

PIHOLE_INTERFACE=tun0
IPV4_ADDRESS=10.8.0.1/24

and restart Pi-hole with sudo service pihole-FTL restart.

  • Create your first VPN profile

You are now ready to create your first profile (profile is file with .ovpn extension). You will need new profile for each device you want to connect to VPN (do not use same profile from multiple devices!). To do this, execute:

pivpn add nopass

Give some recognizable name (I use “<person>-<device>” naming scheme). You can use version with password (omit nopass), but I generally find it really sub-optimal to type password whenever I want to connect (it might be once every couple of days, but still…). After this step, you will get your profile in ovpns directory. Download it to device where you will use it and that’s it. OpenVPN client is generally available for all platforms, so you can download it for Windows, Linux, Android (even from F-Droid), iPhone…Just load .ovpn file in client and you will connect.

  • Customize Pi-hole experience

If you don’t have web port open to access Pi-hole web interface from outside (which I recommend), you can use pi.hole as URI to access it when you are in VPN. Now, visit https://firebog.net and pick lists you want blocked. Paste them in “Settings”->”Blocklists”.

  • Share your setup with others

Each time you fire “pivpn add nopass“, you will generate new profile. You can share this profile with whomever you want, but beware that they will also use same traffic as you and also, you are now in position to see what sites they visit – you should not abuse their trust on this.

That’s it, enjoy your new setup!