android-app icon indicating copy to clipboard operation
android-app copied to clipboard

DNS traffic can leak outside the VPN tunnel on Android

Open Mr-Hitchens opened this issue 9 months ago • 14 comments

We are happy to answer your questions about the code or discuss technical ideas.

Please complete the following checklist (by adding [x]):

  • [x] I have searched open and closed issues for duplicates
  • [x] This isn't a feature request
  • [x] This is not a report about my app not working as expected

Source: https://mullvad.net/en/blog/dns-traffic-can-leak-outside-the-vpn-tunnel-on-android

I am assuming PROTON is also vulnerable to this problem. How are you addressing this problem? As PROTON hasn't updated F-Droid in nearly 5 weeks (Google play is up to date) I'm using a VPN that has addressed this issue as a temporary fix. Is F-Droid not updated because F-Droid has a much more stringent gateway than Google and your app didn't pass inspection or something worse?

Mr-Hitchens avatar May 08 '24 12:05 Mr-Hitchens

GrapheneOS latest OS release, currently in the Beta channel, implements a new feature for blocking DNS leaks by third party VPN service app implementations. The ProtonVPN app is reportedly having issues with the new feature.

GrapheneOS has stated "We'll give it another couple days of testing. Unless our users find an issue with another VPN app, we'll likely ship this to the Stable channel instead of cancelling the current change. We can't hold back an important improvement based on a single app which appears to be buggy."

https://grapheneos.social/@GrapheneOS/112422961319281582

Red00488 avatar May 11 '24 20:05 Red00488

I'll be happy to help test any patch for this, if needed. When the Stable branch of GrapheneOS hits my phone, I imagine I'll have this issue.

edthedev avatar May 13 '24 00:05 edthedev

GrapheneOS latest OS release, currently in the Beta channel, implements a new feature for blocking DNS leaks by third party VPN service app implementations. The ProtonVPN app is reportedly having issues with the new feature.

We did some investigation into GrapheneOS issue and it'll be followed-up here: https://github.com/GrapheneOS/os-issue-tracker/issues/3442#issuecomment-2110739277

mateusz-markowicz avatar May 14 '24 17:05 mateusz-markowicz

It's still in our Beta channel and we don't plan to move it to Stable until we resolve this compatibility issue. It's strange that it only seems to be happening with Proton VPN and it doesn't imply that it's a bug in Proton VPN but it COULD be one where it was depending on a leak happening before. We aren't sure what's wrong yet.

thestinger avatar May 14 '24 17:05 thestinger

@thestinger we managed to reproduce it with some minimal generic VPN app, so it doesn't seem to be anything specific about the client itself. What seems to make the difference is the range our DNS server IP belongs to (10.2.0.1, it's not a public IP and it's accessible only via the tunnel) - if we change it to some public IP like 1.1.1.1 problem goes away - and maybe that's the usual setup for other VPNs (I didn't check that yet, so just speculating) and reason why they are not affected

mateusz-markowicz avatar May 14 '24 17:05 mateusz-markowicz

@mateusz-markowicz do you think you could push this minimal app source code please?

My very vague and speculative hunch is that when the VPN is down, and the killswitch is set in the OS, you have a route for 10.2.0.0/24 in routing rules (or some other range where the DNS server is within it), and due to the VPN being down, and the DNS server being within that range, the OS drops all of that traffic, and there is some form of issue then occurring where it would normally fallback to using OS/user provided DNS server and this is what is breaking atm.

flawedworld avatar May 14 '24 18:05 flawedworld

@flawedworld I'll try to provide the source tomorrow (I'm off for today), but important to note that we observe this behavior on current GrapheneOS beta regardless of whether kill-switch is on or not and DNS starts failing only after VpnService.Builder.establish() when VPN is actually up - we see successful WireGuard handshakes preceding failing DNS queries.

mateusz-markowicz avatar May 14 '24 18:05 mateusz-markowicz

@flawedworld see https://github.com/mateusz-markowicz/minvpn-dns-issue/blob/master/app/src/main/java/proton/example/vpn/WireGuard.kt. We do there HTTPS call just before opening the tunnel (it works) and then a moment after opening a tunnel. If config will have our DNS (10.2.0.1) second call will fail. With some public DNS it'll work fine. @guandalf will contact you about the config

mateusz-markowicz avatar May 15 '24 09:05 mateusz-markowicz

See https://grapheneos.org/releases#2024073100. It should be resolved now in a way we won't have to revert.

thestinger avatar Jul 31 '24 23:07 thestinger

We have a fairly good idea why the behavior you saw was happening and leaving out enforcement for apps not configuring DNS should avoid the issue even though it was not caused by the app not configuring DNS. There's a code path which handles apps setting a netid that's not allowed which gets routed via the VPN DNS if it's configured instead, otherwise it leaks. We believe this code path not having the check will resolve the Proton VPN compatibility issue.

thestinger avatar Jul 31 '24 23:07 thestinger

We could try adding a toggle for blocking leaks when DNS isn't configured by the VPN which would likely be compatible with Proton VPN if we made it only check in that netid error path for the default network leak case instead of the forcing it via VPN case which has no reason to be blocked since it's forcing it through the VPN anyway. It's odd that Proton VPN would ever trigger this code path and that might be an Android bug that gets covered up by the error handling with no real consequence.

thestinger avatar Jul 31 '24 23:07 thestinger

Our Alpha testers are reporting compatibility issues with Proton VPN again, but not any other VPN apps so far.

thestinger avatar Jul 31 '24 23:07 thestinger

Hey @thestinger, which channel was the "mild" fix released on? I am on beta and could not reproduce the previous issue. Could you point me to the results of the findings of the Alpha testers? TY

guandalf avatar Aug 08 '24 06:08 guandalf

You can see our changelog at https://grapheneos.org/releases#changelog or through the Info app in the OS. The releases in Alpha, Beta and Stable are the same production releases. 2024080200 was the initial release with the relaxed fix we were successfully able to ship to Alpha, Beta and then Stable without having to revert it. This blocks connecting to non-VPN DNS. It does not block trying to connect to VPN DNS outside of the VPN, although if the VPN sets private addresses it won't normally get routed past the initial router. It's still problematic. We know how to fully prevent it since that's exactly what we did with our initial attempt in May, but that causes compatibility issues with Proton VPN.

You'll no longer be able to detect DNS leaks for sites/services because it does prevent using anything other than VPN DNS, but doesn't yet make sure that can't leak outside the tunnel. VPN DNS leaking outside the tunnel is rarer than what was happening before but it can still happen if it starts the process of doing a query and the VPN tunnel goes down. It should really enable leak protection there, but as I said it breaks Proton VPN. Proton VPN appears to depend on certain strangeness happening because it's written in a way that it appears to depend on an OS bug or something like that.

thestinger avatar Aug 08 '24 16:08 thestinger