Skip to content

Use shadow tls to Bypass Traffic Billing Systems

ihc童鞋@提不起劲 edited this page Mar 9, 2023 · 3 revisions

Background

Some network traffic metering systems are flawed.

For simplicity of implementation, they tend to consist of an HTTP proxy, an SNI proxy, and billing-related components.

To make it work, the system usually allow some traffic without payment. For example, users must be able to pay securely, so their devices must be able to connect to the payment system in TLS. The payment system like paypal rarely deployed inside their system intranet. Another example is captive: if captive.apple.com is unable to connect, users' iPhones will complain about no networking, which reduced user experience.

Some ISPs which cooperate with popular apps also provide very low price for traffic used by these apps.

Vulnerability

To do these things, it must distinguish traffic, which is hard.

  1. For DNS request: The right way is to build a domain whitelist and block all other domains. It's not hard but lots of systems just ignore it.
  2. For HTTP request: There is usually a domain whitelist inside the http proxy, otherwise everyone can use it without payment. Filtering and proxy HTTP request/response are enough since as a HTTP proxy, it choose destination by itself. If the domain(from header Host) is trusted, and the http request parsing is correct, then it can ensure that the target server and http response are controllable.
  3. For TLS: Usually it works as a SNI proxy, and only relay for domains that in whitelist. This is not enough since the target server is choosed by users, and the proxy can barely change it since a re-resolve may cause problems. The correct way is to build a ip whitelist, which is far harder than building a domain whitelist.

How to Check Vulnerability and Exploit it

For DNS system vulnerability, just resolve any custom domain. If it succeed, it means you can setup a tunnel based on DNS request and response. But we are not going to talk about it.

For TLS, you can use shadow-tls.

Do Some Checking First

  1. curl -vvv https://any_site: if the tcp connection is established instantly, it may means there is a SNI proxy near you.
  2. curl a http request and it should return a redirection, browser it and find domains in developer tools like wireshark or chrome F12.
  3. Lookup these domain until find out a domain with public ip. Recheck and confirm it can be accessed.
  4. curl -vvv --resolve domain:443:1.1.1.1 https://domain: If it shows cloudflare certificate, the vulnerability can be confirmed.

Exploit the Vulnerability

Just choose one of these 2 solutions:

  1. Add the domain to server mapping and restart it(require network access), then config client to use it.
  2. Set the server with wildcard-sni=authed before you are going to lost network access(useful for airplane wifi). You can find available sni and use it in client directly.

Client for different platfroms

  1. Mac: ShadowTlsBinary+ShadowsocksClient / Docker+ShadowsocksClient / Surge
  2. PC: ShadowTlsBinary+ShadowsocksClient(WSL) / Docker+ShadowsocksClient / other third-party client app
  3. iOS: Surge / ShadowRocket
  4. Android: ShadowTlsBinary+ShadowsocksClient / other third-party client app

Note: If you use surge or shadowrocket, you should should not enable v3 mode on server side since it has not been supported yet(v2 is the default protocol version now).