Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Prevent proxy/VPN streaming error messages from Netflix when using an IPv6 tunnelf

Workarounds for Netflix and the blocking of IPv6 tunnels

The dreaded "You seem to be using an unblocker or proxy." error message. Cool story bro.

This gist was essentially created out of my own rant about Netflix being hostile to IPv6 tunnel services since June 2016. You are welcome to read my opinion on the matter, this is the more technical side to the issue and how to combat it within your own network.

Since I wrote this, various GitHub users have contributed their thoughts and ideas which has been incorporated into this gist. Thank you to everyone who have contributed their own methods and implementations.

The problem

Netflix now treats IPv6 tunnel brokers (such as Hurricane Electric) as proxy servers. A while ago it became apparent to users and Netflix that somewhat by accident, IPv6 tunnel users were being served content outside of their geolocation because of the way Netflix was identifying the tunnel services and their geographical origin. The problem was further compounded by certain opportunstic indiviuals deciding to create a business model out of providing the Netflix US (and others) content library via networks like Hurricane Electric and ruined it for everyone. Netflix and friends got all stressy about it and now all IPv6 tunnel users are considered to be naughty proxy pirates. Also because big media is stuck in the 1990s, they think this block is actually effective, when in fact it just inconveniences most legitimate users, that simply want IPv6 connectivity, because their ISP is stuck in 1995.

Netflix has a help article on the matter: https://help.netflix.com/en/node/277

In the early days this article didn't mention anything about IPv6, but now it pretty much spells out if you use a tunnel service for IPv6 you are on your own and won't get any support from Netflix about it, but there is a potential workaround. In order to maintain keeping your IPv6 tunnel active while browsing Netflix you need to basically prevent any traffic to Netflix going over IPv6 and fallback to IPv4, which will likely be using your normal WAN connection from a ISP or provider which Netflix won't treat as a proxy/VPN.

To implement such a workaround you'll need to have a DNS setup that you can fully control. You'll need to have the ability to implement one of the following implementations:

  1. Return a null response on AAAA lookups for certain Netflix domains.
  2. Conditionally forward certain Netflix domain lookups to another DNS resolver that strips AAAA records from lookup responses entirely.
  3. Block or sink hole Netflix IPv6 ranges (not recommended, explained in more detail later on).

This gist focuses on using dnsmasq (commonly found in embedded products i.e. routers) but the overall concept of modifying AAAA lookup responses can be applied to other services like unbound, bind etc.

Netflix domains that need be specially handled

These are the key Netflix domains that need to be handled to prevent IPv6 being used and avoiding a 6in4 tunnel or similar.

  • netflix.com
  • netflix.net
  • nflxvideo.net
  • nflximg.net
  • nflxext.com
  • nflxso.net

Some of these domains may not have AAAA records currently, but its possible this might change in the future, so they are covered off to be future proofed.

Method #1: Return null on AAAA lookups with dnsmasq

The configuration below basically returns an AAAA response with a NULL address on any domains provided. The only downside to this method is you have to generate a matching server and address line for each domain, otherwise you will unwillingly remove A record responses. Your dnsmasq.conf could get quite long very quickly using this method. If you have a bulk load of domains you could write a script to output the server and address lines to a file with the domain being a variable in a loop, fed by a list or another source.

# Null AAAA response on these domains
server=/netflix.com/#
address=/netflix.com/::
server=/netflix.net/#
address=/netflix.net/::
server=/nflxext.com/#
address=/nflxext.com/::
server=/nflximg.net/#
address=/nflximg.net/::
server=/nflxvideo.net/#
address=/nflxvideo.net/::
server=/nflxso.net/#
address=/nflxso.net/::

If you are already running dnsmasq, this is the most simpliest method, without having to worry about additional configurations or services. After this configuration is applied a DNS lookup for a domain in this list would now return ::, which is the NULL response. This would prevent netflix.com requests going over IPv6 and fallback to IPv4.

; <<>> DiG 9.10.3-P4-Raspbian <<>> AAAA netflix.com @127.0.0.1
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 6272
;; flags: qr aa rd ra ad; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 0

;; QUESTION SECTION:
;netflix.com.                   IN      AAAA

;; ANSWER SECTION:
netflix.com.            2       IN      AAAA    ::

;; Query time: 3 msec
;; SERVER: 127.0.0.1#53(127.0.0.1)
;; WHEN: Fri Dec 28 11:23:40 GMT 2018
;; MSG SIZE  rcvd: 57

Method #2: Conditionally forward domains to a resolver that strips AAAA records

A slightly more involved method is to conditionally forward DNS requests for certain Netflix domains to another DNS resolver that will strip AAAA records from domains. In this scenario, there will be another DNS resolver running somewhere in the network.

Using dnsmasq as an example, you can define conditional forward rules like so:

# Resolve these domains with another resolver
server=/netflix.com/127.0.0.1#2053
server=/netflix.net/127.0.0.1#2053
server=/nflxext.com/127.0.0.1#2053
server=/nflximg.com/127.0.0.1#2053
server=/nflxvideo.net/127.0.0.1#2053
server=/nflxso.net/127.0.0.1#2053

127.0.0.1#2053 is the DNS resolver that will resolve the request. The DNS resolver could be anything or running anywhere. In this example, a DNS resolver is running on UDP 2053, in reality this can be anything. I will use bind for the resolver.

Creating a BIND DNS resolver that removes AAAA records from lookups

I chose bind as it has a specific parameter filter-aaaa-on-v4. The example below is a very minimal configuration for bind. Its one purpose is basically to strip AAAA records from DNS lookups. It has the advantage of being domain agnostic, meaning it will strip any AAAA records from any domain passed to it. This is useful if other services other than Netflix start blocking IPv6 tunnels in a similar fashion or simply want to force IPv4 for other services for whatever reason.

options {
	directory "/tmp";
  
 	forwarders {
		208.67.222.222;
		208.67.220.220;
  	};
  
  	forward only;

  	dnssec-enable no;

  	auth-nxdomain no;
  	listen-on port 2053 { 127.0.0.1; };
  	// listen-on-v6 port 2053 { ::1; };
  	filter-aaaa-on-v4 yes;
};

You can use any forwarders you like, the example below uses OpenDNS. If you are running this on an external facing IP address, you should be careful and make sure you only allow recursion on specific requests and ACL accordingly. Not doing so will make you an open DNS resolver, it won't take long for someone to start abusing your server and generating a high rate of traffic.

The --enable-filter-aaaa option must be enabled at compile time in order for this config to work, see this page for more information:

https://kb.isc.org/article/AA-00576/0/Filter-AAAA-option-in-BIND-9-.html

Where this resolver runs is entirely up to you. If you are running something like OpenWRT or DD-WRT you could run bind on a non-standard port like the example to avoid a port collision with an existing DNS setup i.e. dnsmasq.

Confirming AAAA records are removed from DNS lookups

Once everything is setup, you can query any of the following Netflix domains listed above against a public DNS resolver and compare the output to a query made to the additional DNS resolver you've setup.

AAAA DNS request made via Google Public DNS

Google's public DNS servers will always return AAAA records, this is what a typical request to netflix.com will look like:

dig @8.8.8.8 netflix.com AAAA
 
; <<>> DiG 9.9.5-3ubuntu0.8-Ubuntu <<>> @8.8.8.8 netflix.com AAAA
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 21293
;; flags: qr rd ra; QUERY: 1, ANSWER: 8, AUTHORITY: 0, ADDITIONAL: 1
 
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 512
;; QUESTION SECTION:
;netflix.com.                   IN      AAAA
 
;; ANSWER SECTION:
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:fc9
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:177c
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:fed
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:25bf
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:d62
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:1cd2
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:22b2
netflix.com.            59      IN      AAAA    2620:108:700f::36d6:1699
 
;; Query time: 36 msec
;; SERVER: 8.8.8.8#53(8.8.8.8)
;; WHEN: Fri Nov 25 12:51:43 GMT 2016
;; MSG SIZE  rcvd: 264

AAAA DNS request made via the BIND DNS server we setup

Making the same request to our primary DNS resolver that has been configured to strip AAAA records, we should get no AAAA records returned, even if we explicitly request them.

dig @127.0.0.1 netflix.com AAAA
 
; <<>> DiG 9.9.9-P3 <<>> @127.0.0.1 netflix.com AAAA
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 36923
;; flags: qr rd ra; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1
 
;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;netflix.com.                   IN      AAAA
 
;; Query time: 130 msec
;; SERVER: 127.0.0.1#53(127.0.0.1)
;; WHEN: Fri Nov 25 12:51:43 GMT 2016
;; MSG SIZE  rcvd: 40

If you get no AAAA records returned on your DNS resolver with Netflix queries, you're in business. Future Netflix connections should now only use IPv4. If you don't get the expected output this can be due to DNS caching and depending on your setup you might have to wait a bit of time for the correct DNS lookup information to be returned. You can flush the DNS cache of dnsmasq and/or on your local device. Alternatively, you may wish to reboot your router or device supplying DNS to ensure DNS caches are cleared. If you have a DNS chain, you'll need to ensure all DNS resolvers in the chain are not caching.

If you get issues like timeouts, check to make sure the DNS server is actually running and your firewall is permitting the DNS traffic, especially if using a non-standard port for DNS traffic.

Method 3: Blocking Netflix IPv6 ranges (not recommended)

While this method can work, the problem with it is that it is static and not as future proof as DNS related options. The problem is Netflix uses various content delivery networks and obtaining the ranges for them all is difficult. Netflix can also add new IPv6 ranges at anytime. While all of the workaround options can be "broken" by Netflix changing something, in my opinion domain based rules are cleaner than IPv6 ranges. Be mindful that blocking IPv6 ranges may require you to block non-Netflix networks like content delivery networks, which could have side effects for non-related services.

If however you wish to null route or block IPv6 ranges, this can be achieved like so with ip6tables:

ip6tables -I OUTPUT -d 2a01:578:3::/64 -j REJECT
ip6tables -I FORWARD -d 2a01:578:3::/64 -j REJECT

You may have to experiment with additional ranges in order to stop Netflix using IPv6 for your geolocation.

Additional configuration

You may have to implement further changes if you experience problems with Google/Android devices.

Streaming issues with Google Chromecast/Android devices

Devices like Google Chromecast don't allow direct control of the DNS servers used and always try to use Google's Public DNS resolvers (both IPv4 and IPv6), these of course will return AAAA records and will undo any DNS workaround when streaming Netflix from such a device. You can however leverage a fallback option built into Chromecast devices (and likely other Google devices), where by if you block access to the Google Public DNS resolvers, it forces the Chromecast device to use the DHCP supplied DNS information and hence the DNS workaround will work.

An example of doing this with iptables:

iptables -I FORWARD --destination 8.8.8.8 -j REJECT
iptables -I FORWARD --destination 8.8.4.4 -j REJECT

In addition, some Google devices may also make DNS lookup requests over v6 to Google's public DNS servers, you may have to also block this traffic as well:

ip6tables -I FORWARD --destination 2001:4860:4860::8844 -j REJECT
ip6tables -I FORWARD --destination 2001:4860:4860::8888 -j REJECT

REJECT is a bit more friendly than DROP in this case, as the "fail" response will be quicker. You want the request to fail quickly in this case. You'd use DROP in a more defensive/security scenario.

If you happen to use Google's DNS resolvers at the network level for general DNS queries you can limit this block to the IP address of your Chromecast device with the -s option, allowing you to use Google's DNS resolvers for other devices still. This would require you to use static DHCP in order to create a fixed LAN IP address for any Chromecast devices you have, so you know where they are on the network.

Intercepting Google DNS traffic, rather than blocking

There are several reports that some Google based devices like Android tablets don't seem to like having the Google public DNS resolvers sinkholed. If you experience problems streaming with devices like Chromecasts, Google tablets etc. after blocking Google DNS requests, you might want to instead intercept the requests rather than block them. This can also be achieved via iptables:

iptables -t nat -A PREROUTING -s 192.168.x.x/24 -d 8.8.8.8 -p udp --dport 53 -j DNAT --to 192.168.x.x
iptables -t nat -A PREROUTING -s 192.168.x.x/24 -d 8.8.4.4 -p udp --dport 53 -j DNAT --to 192.168.x.x
  • 192.168.x.x/24 - Range of your LAN, example: 192.168.1.0/24
  • 192.168.x.x - The device that is running DNS i.e. router 192.168.1.1

This method essentially allows DNS requests to 8.8.8.8 or 8.8.4.4, but the request itself will be intercepted and actually resolved by a DNS server of the users choosing, alebit transparently. You can run the Google DNS test example if you apply this method and confirm that no AAAA records are returned, because the DNS server used was actually something else.

DNS traffic is typically UDP based, but there are circumstances where TCP is used as well, however, it is unlikely any Google DNS request will be using TCP, hence why the rules above only target UDP and should be fine for this purpose.

To implement this, you'll need to have a full root access to your router.

Enjoy your Netflix again!

Extra Q&A bit

In case you have any questions about the purpose/reasons for this workaround, here's some answers to potential questions you might have.

Q. Will I be able to stop using this workaround at some point?

A. Once your ISP provides a native IPv6 subnet to you, you can disable your IPv6 tunnel and use the IPv6 subnet delegated to you by your ISP (likely a /56 or something similar).

To clarify, Netflix is only blocking IPv6 tunnels because it cannot accurately confirm your exact country of origin and sees any usage of a IPv6 tunnel as a way of circumventing geo-restrcitions on content that is licensed to specific countries, despite this being the intention or not. In the case of Hurricane Electric, while it operates tunnels in loads of different countries, the IPv6 address space they have registered ultimately identifies as US to a lot of geo based systems concerning IPv6. This problem however is now redundant as Netflix has now straight blocked the IPv6 ranges of various IPv6 tunnel services altogether.

Q. I use a VPN and I get the same error message, will this workaround work for this?

A. Using a VPN with Netflix is very tricky because Netflix actively blocks such services. You'll likely want to look at something called split tunnelling where by you have a VPN connection active, but send Netflix traffic through your WAN (non VPN gateway). This however is out of scope of what is achieved with the information in this gist.

Q. Will Netflix block my actual normal ISP connection?

A. They shouldn't do. When you use your ISPs connection, the IP address you connect from shouldn't be considered a proxy/VPN.

Q. How does this workaround work?

A. In short, the workaround forces Netflix to use IPv4 for any requests when streaming. While you might think "why can't I just to make things use IPv4 first?" in reality, this is both against the general behaviour of IPv6 first (happy eyeballs) and difficult to actually enforce. Especially if you need to do this across different devices. Hence doing it at the router/DNS level allows you to control all variables required. This does require a bit of technical knowledge and control over your network however and might not be for everyone admittedly.

Fun fact: Netflix has supported IPv6 for many years. IPv6 itself isn't the issue and something which we should be encouraging adoption of. The problem is for more tech savvy users that don't have native IPv6 from their ISP have opted to use a tunnel service for it instead. Since June 2016, Netflix shut off streaming access to its service for IPv6 tunnels services and this has what's caused the problem. Netflix's easy solution to this is to "disable" or stop using a IPv6 tunnel. However this isn't practical for many people and negates the reason having one in the first place.

Q. Will this workaround stop working in the future?

A. Depending on how you implemented it, it should be pretty robust, but if Netflix introduce a new domain not covered in the list above that has some form of IPv6 connectivity test which then determines proxy/VPN usage, it may have to be expanded, I have personally used this workaround since June 2016 and it hasn't let me down yet.

Q. Does this workaround allow me to bypass geo-restrictions?

A. No. It is simply designed to allow connectivity to Netflix, while having an IPv6 tunnel active. This does not allow you to obtain access to library content outside your region. This is basically the reason why this workaround had to be implemented in the first place for us legit IPv6 tunnel users. This is why we can't have nice things!

Q. Will Netflix unblock IPv6 tunnels in the future?

A. Probably not, they were likely pressured into it in the first place by media companies and license holders. Once the secret was out about how IPv6 tunnels were providing access to what should have been geo-restricted content, action was swiftly taken. To be honest, Netflix probably doesn't care that much about this (as long as your paying your monthly subscription!). It was more likely being lent on by higher powers, hence the rather bold straight blocking approach.

Its also worth noting that IPv6 tunnel services are intended as transitional mechanisms and shouldn't be a permanent solution for IPv6. Hassle your ISP to sort out their IPv6 (or lack of!). While you wait you can also read the hilarious IPv6 excuses Twitter account for some nerdy IPv6 banter: https://twitter.com/ipv6excuses?lang=en.

Q. Do any proxy/VPN services still work with Netflix?

A. There are likely some services that might still work, but they are likely operating on borrowed time, as Netflix will be monitoring and updating their blocklists regularly. Most of the well known proxy/VPN services are blocked.

Q. I'm not able to install additional software like bind, are there any alternatives?

A. Yes. There is a excellent lightweight DNS proxy specifically for Netflix IPv6 tunnel purposes. Written in Python, it should work on most Unix/Linux systems with little setup required.

https://github.com/cdhowie/netflix-no-ipv6-dns-proxy

The same concept applies, you need to have your primary DNS resolver forward requests to this proxy, be aware this DNS proxy is specifically for Netflix domain usage and won't strip the AAAA records of other domains if sent to it. You can edit the source code to expand it if you wanted to though.

Q. Who is "big media"?

A. My pet name for the media rights corporations who are probably in the illuminati stuck in the past and clearly don't understand technology.

@seiferma

This comment has been minimized.

Copy link

@seiferma seiferma commented Jun 18, 2017

Thanks for your extensive manual. I was able to watch Netflix again.

However, I experienced problems with hard coded DNS servers with my tablet as well, which might be caused by an old version of the Netflix app. I could not watch videos when blocking the Google DNS servers. Instead, I redirected the requests with destination NAT as follows:
iptables -t nat -A PREROUTING -s 192.168.0.0/24 -d 8.8.8.8 -p udp --dport 53 -j DNAT --to 192.168.0.1

You might want to include this solution in your manual.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Jun 25, 2017

@seiferma Thanks for your response! Sadly Github didn't notify me of the comment on this gist. I will update the information sure, thanks for report!

@almaslegacy

This comment has been minimized.

Copy link

@almaslegacy almaslegacy commented Sep 20, 2017

My kingdom for simple detailed plain english instructions here.

@iphoting

This comment has been minimized.

Copy link

@iphoting iphoting commented Dec 24, 2017

Consider the following configuration for dnsmasq:

server=/netflix.com/#
address=/netflix.com/::
server=/netflix.net/#
address=/netflix.net/::
server=/nflxext.com/#
address=/nflxext.com/::
server=/nflximg.net/#
address=/nflximg.net/::
server=/nflxvideo.net/#
address=/nflxvideo.net/::
server=/nflxso.net/#
address=/nflxso.net/::

Adapted from: https://forums.he.net/index.php?topic=3564.msg20916#msg20916

@CraigHumphrey

This comment has been minimized.

Copy link

@CraigHumphrey CraigHumphrey commented Dec 26, 2017

Windows users can also use the following "fix" from Microsoft, to prefer IPv4 addresses over IPv6.

Article HERE

Use the download that says "Prefer IPv4 over IPv6 in prefix policies"

@seiferma

This comment has been minimized.

Copy link

@seiferma seiferma commented Jan 6, 2018

I had to block the IPv6 addresses of the google dns servers in order to watch Netflix on my chromecast device today. They might have hard coded these addresses as well. The fallback to IPv4 dns servers (which are covered in your manual) works.

I added the following lines to my firewall configuration

ip6tables -I FORWARD --destination 2001:4860:4860::8844 -j REJECT
ip6tables -I FORWARD --destination 2001:4860:4860::8888 -j REJECT
@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Jan 23, 2018

@iphoting This seems like a more simpler solution for dnsmasq resolvers. I'll check it out.

@CraigHumphrey I'd discourage that approach, because IPv6 is meant to be tried first. There's also no guarantee that the policy will be honoured. I believe I tested it a Windows box once and I still had issues. I think DNS is the "better" way to fix it (its a hack either way without native IPv6), but it is more complicated and in some cases you won't have the level of control over the network to do it.

@seiferma Thanks for letting me know. I know the Google DNS servers have been available over v6 for sometime. Perhaps only certain Chromecast apps are doing v6 DNS lookups to the Google resolvers more recently.

@csdexter

This comment has been minimized.

Copy link

@csdexter csdexter commented Apr 6, 2018

Thanks for taking the time to write this and a heartfelt booo to Netflix for handling the issue caveman style. I would like to add to your text that you don't need to reboot machines after making the change: any BIND instance can be told to forget its cache via rndc flush, any dnsmasq instance can do the same via a service dnsmasq restart and any (poor) Windows client can use ipconfig /flushdns. See, no need to reboot the whole machine :-D

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Apr 30, 2018

@csdexter Thanks for your recommendation! It is indeed somewhat overkill to reboot, but sometimes its just easier, given the varying commands to flush the DNS cache. Lazy I know, but I tried to be as generic as possible with examples, so the generic concept can be applied to different DNS resolvers, setups etc.

@puggan

This comment has been minimized.

Copy link

@puggan puggan commented Jun 21, 2018

Blocking the netflix-ipv6 adresses worked for me.

ip6tables -A OUTPUT -d 2a01:578:3::/64 -j REJECT
ip6tables -A FORWARD -d 2a01:578:3::/64 -j REJECT
@imbaczek

This comment has been minimized.

Copy link

@imbaczek imbaczek commented Aug 14, 2018

dnsmasq #1 worked great for me on tomato (freshtomato-arm https://openlinksys.info/forum/viewthread.php?thread_id=21651).

@mrghosh

This comment has been minimized.

Copy link

@mrghosh mrghosh commented Oct 30, 2018

Thank you for such a great article. I was a little bit confused about the dnsmasq Method#1 configurations. At first, I only added address=/netflix.com/:: in the configuration file, but the DNS query didn't return any ipv4 A records. Then, I added server=/netflix.com/# and the ipv4 records were returned.

From the manual:

The special server address '#' means, "use the standard servers", so --server=/google.com/1.2.3.4 --server=/www.google.com/# will send queries for *.google.com to 1.2.3.4, except *www.google.com which will be forwarded as usual.

Then after some trial, I understood that:
If we specify ipv4 or ipv6 address and omit the server # line, then only that specified ipv4/ipv6/both will be returned. No query will be sent to the upstream DNS server, but if we specify ipv6 address and the server #, then dnsmasq will query the upstream DNS server for ipv4 records and return those with our specified ipv6 IP. Similarly, if we specify ipv4 address and server #, then dnsmasq will query the upstream DNS server for ipv6 records and return those with our specified ipv4 IP.

My config:

...
server=/jio.com/#
address=/jio.com/::
log-queries

nslookup

C:\WINDOWS\system32> nslookup sngprcdnems01.cdnsrv.jio.com
Server: GL-AR150.lan
Address: fd49:6a12:b99a::1
Non-authoritative answer:
Name: sngprcdnems01.cdnsrv.jio.com
Addresses: ::
49.44.53.234

From my log:

Tue Oct 30 13:17:18 2018 daemon.info dnsmasq[9372]: started, version 2.78 cachesize 150
...
Tue Oct 30 13:17:18 2018 daemon.info dnsmasq[9372]: using nameserver 8.8.8.8#53
Tue Oct 30 13:17:18 2018 daemon.info dnsmasq[9372]: using standard nameservers for domain jio.com
...
Tue Oct 30 13:21:12 2018 daemon.info dnsmasq[9372]: query[A] sngprcdnems01.cdnsrv.jio.com from fd49:6a12:b99a::a1c8:fda4:3434:b54d
Tue Oct 30 13:21:12 2018 daemon.info dnsmasq[9372]: forwarded sngprcdnems01.cdnsrv.jio.com to 8.8.8.8
Tue Oct 30 13:21:12 2018 daemon.info dnsmasq[9372]: reply sngprcdnems01.cdnsrv.jio.com is 49.44.53.234
Tue Oct 30 13:21:12 2018 daemon.info dnsmasq[9372]: query[AAAA] sngprcdnems01.cdnsrv.jio.com from fd49:6a12:b99a::a1c8:fda4:3434:b54d
Tue Oct 30 13:21:12 2018 daemon.info dnsmasq[9372]: config sngprcdnems01.cdnsrv.jio.com is ::

You wrote that

This config hack, basically prevents AAAA from being returned by dnsmasq

The above is not true. Dnsmasq returns AAAA but it is :: which is a NULL address. From the manual:

Note that NULL addresses normally work in the same way as localhost, so beware that clients looking up these names are likely to end up talking to themselves.

However, most probably the client OS just ignore these addresses and uses the ipv4 IP.

@GTAdoum

This comment has been minimized.

Copy link

@GTAdoum GTAdoum commented Dec 9, 2018

Blocking the netflix-ipv6 adresses worked for me.

ip6tables -A OUTPUT -d 2a01:578:3::/64 -j REJECT
ip6tables -A FORWARD -d 2a01:578:3::/64 -j REJECT

I live in Canada with an HE IPv6 tunnel on an OpenWRT router, this command worked in my case :
ip6tables -I FORWARD -d 2406:da00:ff00:0::/64 -j REJECT

-I instead of -A, to have the rule at beginning of the chain, otherwise it was not working.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Dec 29, 2018

@souravndp Thanks for testing the dnsmasq AAAA null method more in-depth. You are absolutely correct and I've rewrote a chunk of the original information to clarify these details. I personally use this method now given I was already using dnsmasq.

According to sources the null response is known as an "unspecified address"

https://tools.ietf.org/html/rfc3513#section-2.5.2

Like you've said, I assume clients treat it like having no AAAA.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Dec 29, 2018

@GTAdoum You'll probably to have to keep blocking additional IPv6 ranges in a cat and mouse fashion. It's generally not a recommend approach because it can easily be undone.

@oscrx

This comment has been minimized.

Copy link

@oscrx oscrx commented Feb 17, 2019

Thanks!

@doctorjames

This comment has been minimized.

Copy link

@doctorjames doctorjames commented Apr 28, 2019

For anyone using knot-resolver such as on a Turris Omnia, the following custom lua config seems to work placed in /etc/kresd.custom.conf:

local function filterAAAA (state, req)
 	local qry = req:current()
 	if qry.stype == kres.type.AAAA then
 		return kres.DONE
 	end
 	return state
end

-- block netflix ipv6 resolution as it blocks tunnelbroker
policy.add(policy.suffix(filterAAAA, policy.todnames({'netflix.net.', 'netflix.com.', 'nflxext.com.', 'nflximg.com.', 'nflxvideo.net.', 'nflxso.net.'})))
@jochena

This comment has been minimized.

Copy link

@jochena jochena commented May 14, 2019

Chromecast is using DNS over TLS, now. So it has become necessary to also block dns.google.com in order to get the Chromecast to stream Netflix. It resolves to one IPv4 and one IPv6, at the moment. And they are different to the IP addresses of the normal DNS servers.

@amery

This comment has been minimized.

Copy link

@amery amery commented Jun 21, 2019

Consider the following configuration for dnsmasq:

server=/netflix.com/#
address=/netflix.com/::
server=/netflix.net/#
address=/netflix.net/::
server=/nflxext.com/#
address=/nflxext.com/::
server=/nflximg.net/#
address=/nflximg.net/::
server=/nflxvideo.net/#
address=/nflxvideo.net/::
server=/nflxso.net/#
address=/nflxso.net/::

Adapted from: https://forums.he.net/index.php?topic=3564.msg20916#msg20916

same but for openwrt, confirmed to work from the UK (VM) with ipv6 via he.net

#!/bin/sh

set -eux

# Null AAAA response on these domains
for x in netflix.com netflix.net nflxext.com nflximg.net nflxvideo.net nflxso.net; do
	uci add_list "dhcp.@dnsmasq[0].address=/$x/::"
	uci add_list "dhcp.@dnsmasq[0].server=/$x/#"
done
uci commit dhcp
service dnsmasq restart
@Kline-

This comment has been minimized.

Copy link

@Kline- Kline- commented Jun 26, 2019

For anyone already running BIND9 here is a very stripped down config to start with. You just need to setup a second IP address on your BIND9 host so you have one instance listening on two ports instead of running two separate instances.

options {
    forwarders {
        // Google public DNS
        8.8.8.8;
        8.8.4.4;
        2001:4860:4860::8888;
        2001:4860:4860::8844;
        // OpenDNS
        208.67.222.222;
        208.67.220.220;
        2620:0:ccc::2;
        2620:0:ccd::2;
        // HE.net
        74.82.42.42;
        2001:470:20::2;
    };
        
    listen-on port 53 { 127.0.0.1; 10.0.1.1; };
    listen-on-v6 port { 127.0.0.1; 10.0.1.1; };
    listen-on port 5353 { 10.255.255.254; };
    listen-on-v6 port 5353 { 10.255.255.254; };
};

view "ipv4only" {
    match-destinations { 10.255.255.254/32; };
    filter-aaaa-on-v4 yes;
};

view "normal" {
    match-clients { localhost; 10.0.0.0/8; }
    
    zone "netflix.com" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };

    zone "netflix.net" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };

    zone "nflxvideo.net" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };

    zone "nflximg.net" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };

    zone "nflxext.com" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };

    zone "nflxso.net" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
    };
};
@CRTX

This comment has been minimized.

Copy link

@CRTX CRTX commented Aug 6, 2019

Chromecast is using DNS over TLS, now. So it has become necessary to also block dns.google.com in order to get the Chromecast to stream Netflix. It resolves to one IPv4 and one IPv6, at the moment. And they are different to the IP addresses of the normal DNS servers.

How do you do this?

@jochena

This comment has been minimized.

Copy link

@jochena jochena commented Aug 11, 2019

Chromecast is using DNS over TLS, now. So it has become necessary to also block dns.google.com in order to get the Chromecast to stream Netflix. It resolves to one IPv4 and one IPv6, at the moment. And they are different to the IP addresses of the normal DNS servers.

How do you do this?

I was trying to block all IP addresses associated with dns.google.com. But I never had them all and my infrastructure (a FritzBox router) was not very good for all that. I have a bought a mini-pc with Debian as a router in front of the DSL box.

Google did release their DNS over TLS into production mode, now, which means dns.google.com has been switched off and replaced by their multicast addresses: dns.google (8.8.8.8; 8.8.4.4; 2001:4860:4860::8888; 2001:4860:4860::8844). These can be blocked with a suitable firewall.

Unfortunately my Chromecast does not seem to fallback to my networks DNS anylonger. Paul Vixie (DNS inventor) had the same problem and complaint made the rounds on various news sites. I do what he does and redirect 8.8.8.8 to my DNS servers IP address (using DNAT) and block the rest. But you need a firewall that can do that. Easy for any Linux box, I don't know if some consumer routers can do it.

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 25, 2019

Hi,
I've been using the dnsmasq method for a while now, and indeed I can confirm that the doc is right, and null addresses definitely behaves like localhost, so machines looking up these :: try to talk to themselves. So when I go on netflix.com in my web browser I have to wait about a minute and regularly press f5 for it to stop telling me the website can't be reached and try ipv4. Anyone has any idea how I work around this ?

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Oct 25, 2019

@xogium The null address isn't related to localhost I don't believe. It's a specific type of address explained in the RFC:

https://tools.ietf.org/html/rfc3513#section-2.5.2
https://en.wikipedia.org/wiki/IPv6_address#Unspecified_address
http://www.omnisecu.com/tcpip/ipv6/ipv6-loopback-address-and-ipv6-unspecified-address.php

Localhost in IPv6 terms is ::1/128. An unspecified address is ::/0, so they differ.

Whether or not the use of an unspecified address is ideal for this purpose or against the RFC, debatable, but it seems to work and with dnsmasq slightly less code required to implement.

Happy eyeballs should be in play so the delay between a device falling back to IPv4 shouldn't be that long. The DNS response should pretty much make a device ignore IPv6. What specific device/browser are you using?

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 25, 2019

Hi,
I'm using archlinux with chromium 78 as browser, but this sort of stuff also happened with firefox 70.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Oct 25, 2019

Interesting. I've not experienced long delays with dnsmasq + unspecified address/null responses. You certainly shouldn't get that type of behaviour on modern browsers, as they will have implemented happy eyeballs. I'd look at your network config and dnsmasq setup.

Have you tried doing DNS queries directly from command line, is the DNS response slow? Perhaps one or more resolvers in your chain are misbehaving?

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 25, 2019

when I do a ping from command line the ip is automatically resolved to ipv4. However when I try to do this
ping -6 netflix.com
I get:
From _gateway (fe80::1053:25ff:feed:9ee9%br0) icmp_seq=9 Destination unreachable: Beyond scope of source address

I have no idea if this is expected or not. Also dns queries with dig take about 1 msec, both for netflix.com and netflix.com AAAA.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Oct 25, 2019

Looks like there's a potential config issue. Testing on my DD-WRT router, I get ping responses, interestingly from localhost, so I think you were right about how such addresses are treated, I didn't know.

ping -6 netflix.com
PING netflix.com (::): 56 data bytes
64 bytes from ::1: seq=0 ttl=64 time=0.286 ms
64 bytes from ::1: seq=1 ttl=64 time=0.187 ms
64 bytes from ::1: seq=2 ttl=64 time=0.534 ms
64 bytes from ::1: seq=3 ttl=64 time=0.222 ms
64 bytes from ::1: seq=4 ttl=64 time=0.220 ms
64 bytes from ::1: seq=5 ttl=64 time=0.214 ms
root@NETGEAR-R7000:~# dig AAAA netflix.com

; <<>> DiG 9.12.3-P4 <<>> AAAA netflix.com
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 15483
;; flags: qr aa rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;netflix.com.                   IN      AAAA

;; ANSWER SECTION:
netflix.com.            2       IN      AAAA    ::

;; Query time: 12 msec
;; SERVER: 192.168.1.1#53(192.168.1.1)
;; WHEN: Fri Oct 25 21

The destination unreachable seems to be the problem for you.

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 25, 2019

Alright, so there's that. Other than the ping response that seems kind of weird, my dig query is exactly the same as yours. This is strange. That said when I try to ping :: itself I get the same thing. I will have to investigate this more. I'll report back if I find something :)

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 25, 2019

So turns out it is valid, in a sense. You can't ask to get to :: with a fe80 address which is what my system seems to be trying. :: is outside of the scope of the link local address, so this will obviously not work. However my default gateway is exactly this, a fe80 address. Not sure how to solve this at this point.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Oct 26, 2019

Interestingly. fe80 is a valid default gateway I believe. I looked at mine and it's fe80::2e30:33ff:feed:fd21%10.

What happens when you go to https://test-ipv6.com?

@xogium

This comment has been minimized.

Copy link

@xogium xogium commented Oct 26, 2019

It detect both my ipv4 and ipv6. I have dhcpv6 configured alongside slaac.

@jdlightfoot

This comment has been minimized.

Copy link

@jdlightfoot jdlightfoot commented Dec 3, 2019

I'm trying to run Netflix and I use an HE ipv6 tunnel. In the past, I was able to null-route the Netflix ipv6 ranges, but I can't keep up anymore. I'm trying to implement solution #1 above, but it doesn't work for me. I'm running ASUS Merlin and added the following to dnsmasq.postconf in the /jffs/scripts directory:

#!/bin/sh
#Null AAAA response on these domains
server=/netflix.com/#
address=/netflix.com/::
server=/netflix.net/#
address=/netflix.net/::
server=/nflxext.com/#
address=/nflxext.com/::
server=/nflximg.net/#
address=/nflximg.net/::
server=/nflxvideo.net/#
address=/nflxvideo.net/::
server=/nflxso.net/#
address=/nflxso.net/::
touch /jffs/scripts/dnsmasq-postconf-last-run.txt

Can anyone help me figure out why it's not working? One strange thing I notice is that the file dnsmasq-postconf-last-run.txt is created when I restart my router, but the date and time on it is always May 5, 2018 at 0:00.

Thanks very much

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Dec 3, 2019

I don't know ASUS Merlin firmware very well, but perhaps this might help:

https://github.com/RMerl/asuswrt-merlin/wiki/Custom-config-files

For dnsmasq, the path to append custom config lines would be: /jffs/configs/dnsmasq.conf.add. Perhaps this might work compared to the postconf option.

Potentially it could be a syntax or parsing problem with the file itself, but you'd have to test it.

@jdlightfoot

This comment has been minimized.

Copy link

@jdlightfoot jdlightfoot commented Dec 3, 2019

Thanks, James. My issue now is when i try it as /jffs/configs/dnsmasq.conf.add, it seems to be doing exactly the opposite of the behavior I want -- disabling ipv4 to Netflix and letting ipv6 in.

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Dec 4, 2019

Not sure I'm afraid, that config works with vanilla dnsmasq. The use of both the server and address is specifically deigned to make sure you don't lose IPv4. I can only guess that because of the way ASUS Merlin parses configs it's not being applied/interpreted correctly.

@JWSmythe

This comment has been minimized.

Copy link

@JWSmythe JWSmythe commented Dec 21, 2019

I had to expand on your IP blocks. I had written another script to go through the domains, but they have an abundance of subdomains that were troublesome on simple dig requests. These blocks were identified with my other script, and looking a what Chrome's IPvFoo extension showed for active connections on IPv6. If you think the list is old, just watch what blocks are used with IPvFoo.

Sadly, the ISP I'm on doesn't seem to intend to provide IPv6 to users anytime in the near future. This HE tunnel was my only choice to try to prepare for the IPv6 transition. I use it to provide IPv6 service to all the devices on my home network.

[Edit 2020-Apr-05: A few months ago, I did a major restructuring on my network, and switched over to the dnsmasq filtering. Anyone else trying will have to look into what they're resolving as, and update the blocks as appropriate. I did notice that thingiverse.com and fandom.com sometimes have problems with HE. The dnsmasq technique can fix those too.]

#!/bin/sh
ip6tables -I INPUT -d 2a01:578:3::/64 -j REJECT
ip6tables -I OUTPUT -d 2a01:578:3::/64 -j REJECT
ip6tables -I FORWARD -d 2a01:578:3::/64 -j REJECT

# Discovered these with fix_netflix.php script
ip6tables -I INPUT -d 2406:da00:ff00::/64 -j REJECT
ip6tables -I OUTPUT -d 2406:da00:ff00::/64 -j REJECT
ip6tables -I FORWARD -d 2406:da00:ff00::/64 -j REJECT

ip6tables -I INPUT -d 2a00:86c0:2091::/64 -j REJECT
ip6tables -I OUTPUT -d 2a00:86c0:2091::/64 -j REJECT
ip6tables -I FORWARD -d 2a00:86c0:2091::/64 -j REJECT

ip6tables -I INPUT -d 2600:1406:3c::/64 -j REJECT
ip6tables -I OUTPUT -d 2600:1406:3c::/64 -j REJECT
ip6tables -I FORWARD -d 2600:1406:3c::/64 -j REJECT

@jamesmacwhite

This comment has been minimized.

Copy link
Owner Author

@jamesmacwhite jamesmacwhite commented Dec 25, 2019

@JWSmythe The example IPv6 blocks are by no means an exhaustive, depending on your geolocation, you will need sinkhole various IPv6 address spaces under the Netflix AS. I don't recommend blocking IPv6 ranges because it is very static and can easily be broke, if Netflix traffic goes over a range not blocked.

While you've inspected the traffic, you can't be 100% sure that it won't change. It's why the DNS based approach is better. It is slightly more dynamic.

I included the IPv6 range blocking approach as a fallback in the event you can't control your DNS setup, but whatever works I guess!

@leshniak

This comment has been minimized.

Copy link

@leshniak leshniak commented Feb 8, 2020

According to RFC:
ip route add prohibit 100::1/128

then in dnsmasq conf:

server=/netflix.com/#
address=/netflix.com/100::1
server=/netflix.net/#
address=/netflix.net/100::1
server=/nflxext.com/#
address=/nflxext.com/100::1
server=/nflximg.net/#
address=/nflximg.net/100::1
server=/nflxvideo.net/#
address=/nflxvideo.net/100::1
server=/nflxso.net/#
address=/nflxso.net/100::1

IPv4 fast fallback should do the rest of the trick.

@PaTTeeL

This comment has been minimized.

Copy link

@PaTTeeL PaTTeeL commented Mar 12, 2020

@leshniak I've read the RFC6666
Per this document, IANA has recorded the allocation of the IPv6 address prefix 0100::/64 as a Discard-Only Prefix in the "Internet Protocol Version 6 Address Space" and added the prefix to the "IANA IPv6 Special Purpose Address Registry" [IANA-IPV6REG].
So shall I use 100:: instead ?

@zserik

This comment has been minimized.

Copy link

@zserik zserik commented Apr 25, 2020

BIND9 rpz zone generator to avoid "filter-aaaa-on-v4", which doesn't work if other AAAA records should be resolved. (e.g. yet another work-around)...
https://gist.github.com/zserik/364c65051106546ae2b6f52b0b0bc282

@Kline-

This comment has been minimized.

Copy link

@Kline- Kline- commented Apr 25, 2020

@zserik
Am I missing something? I still have filter-aaaa-on-v4 working fine and only blocking Netflix. I had to make some minor config adjustments after updating BIND today since filter-aaaa moved to a plugin instead.

dig @10.0.1.1 aaaa netflix.com

; <<>> DiG 9.10.3-P4-Debian <<>> @10.0.1.1 aaaa netflix.com
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 12418
;; flags: qr rd ra; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;netflix.com.                   IN      AAAA

;; Query time: 4 msec
;; SERVER: 10.0.1.1#53(10.0.1.1)
;; WHEN: Sat Apr 25 17:35:58 CDT 2020
;; MSG SIZE  rcvd: 40

dig @10.0.1.1 aaaa google.com

; <<>> DiG 9.10.3-P4-Debian <<>> @10.0.1.1 aaaa google.com
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 24290
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
;; QUESTION SECTION:
;google.com.                    IN      AAAA

;; ANSWER SECTION:
google.com.             246     IN      AAAA    2607:f8b0:4009:804::200e

;; Query time: 40 msec
;; SERVER: 10.0.1.1#53(10.0.1.1)
;; WHEN: Sat Apr 25 17:34:52 CDT 2020
;; MSG SIZE  rcvd: 67

This was the change to remove filter-aaaa-on-v4 from the global options block and instead place it within the appropriate view:

view "ipv4only" {
    plugin query "filter-aaaa.so" { filter-aaaa-on-v4 yes; };
    match-destinations { 10.255.255.254/32; };
};

All of the Netflix domains are stub zones like the following:

zone "netflix.com" {
        type forward;
        forward only;
        forwarders { 10.255.255.254 port 5353; };
};
@zserik

This comment has been minimized.

Copy link

@zserik zserik commented Apr 25, 2020

@Kline- nope, not missing anything, just what I came up with, alternatively...

@Kline-

This comment has been minimized.

Copy link

@Kline- Kline- commented Apr 25, 2020

@zserik Ok, thanks! Your first reply was not long after I updated BIND today, breaking this and my RPZ setup. I just finished getting it all sorted back and wasn't sure if I overlooked something in the process!

@leshniak

This comment has been minimized.

Copy link

@leshniak leshniak commented Oct 17, 2020

For people using dnscrypt-proxy: I've made a PR that allows to (in short) prefer IPv4 connection instead of IPv6, leaving IPv6-only sites still accessible.

https://github.com/DNSCrypt/dnscrypt-proxy/pull/1495/files

I don't know if it's gonna be merged, but you can easily compile your own binary.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.