TL;DR: Windows 10 DNS resolver sends DNS requests in parallel to all available network interfaces and uses the fastest reply to come. If you use DNS from the local network, this problem allows your ISP or a hacker with Wi-Fi ap to hijack your DNS records even if you use VPN.

Modern Windows versions add headaches to active VPN users. DNS resolver in earlier versions up to Windows 7 was predictable and made DNS requests in order according to DNS servers preference, just as all other OS. This could lead to DNS Leak only if the DNS server inside the tunnel didn’t reply in time or sent en error, which wasn’t that horrible.

Windows 8

With Windows 8 release, Microsoft added a pretty interesting function called ‘Smart Multi-Homed Name Resolution’ which was passed over in silence as I can say using Google. It’s enabled by default, and if it’s enabled, OS sends queries to all known DNS servers via all available network interfaces, binding query to the interface. That’s probably done to speed up DNS resolving in case of preferred server failure or timeout (1 second by default) so the answer from the second server would be immediately returned to the application. In this case, all your queries are leaked via network interface which allows your ISP or Wi-Fi ap owner to monitor all the websites you visit. DNS Leak is only possible if your route table allows to forward DNS queries via internet interface. This is a typical situation for 99% SoHo routers as they set up their own caching DNS servers on their local IP address.

This feature could be disabled via registry editor. You should add a DWORD value with the name

DisableSmartNameResolution

To the registry path

HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows NT\DNSClient

with any value except zero.

Windows 10

Even if Windows 8 and 8.1 send all your DNS requests via public interface, dns spoofing is hard to do because OS would use hijacked answer only if your main DNS server (which goes via encrypted VPN connection) is failed to respond.

Everything changed when it comes to Windows 10. Now OS not only just sends DNS requests to all interfaces, it even uses the fastest one response to receive. This allows your ISP or a hacker to hijack your DNS really easy and reliable. Moreover, you can’t disable ‘Smart Multi-Homed Name Resolution’ in Windows 10, registry key which worked for Windows 8.1 doesn’t work now.

The only acceptable (but not fully reliable) way to workaround this issue is to explicitly set DNS on your network interface somewhere out of your local segment, like well-known 8.8.8.8 but it won’t help for OpenVPN. The only way to avoid DNS leaks in OpenVPN is to use scripts which temporary disable all DNS on external interfaces.

UPD: earlier I recommended to use redirect-gateway option without def1 parameter for OpenVPN. It seems that Windows reverts default route back on every DHCP renew and all your traffic would bypass VPN connection in some time after connect. There is no good fix for OpenVPN yet.

UPD2: I wrote a plugin to fix this issue.

UPD3: Plugin functionality has been integrated in OpenVPN 2.3.9. Use block-outside-dns option.