注:本文原作于2018年1月11日,其中所包含的一些信息可能已不再适用。
警告:技术无罪,莫用作非法用途。如进行不合理使用所造成任何法律责任,笔者概不负责。
迁入大学校内的宿舍后,我对垄断该宿舍的网络公司所使用的认证系统进行了一番研究。
1.初探
该认证系统在未登录时封锁除53、80及443以外的所有TCP端口;UDP未予详细测试,但至少知道UDP/53(DNS)应该未被其封锁/篡改——经测试,未登录时DNS也能返回正确的记录,无论通过TCP还是UDP进行查询。
该系统登录页面具有域名(下以a.net代称),并使用了HTTPS。值得注意的是,这个系统可以在未连接该网络时访问,此时登陆账户,不能上线,只能查看账户信息或充值等;通过nslookup
可知其使用了CloudFlare的CDN。
未登录时,通过HTTP(TCP/80)访问任何网站,会被其网关302重定向至https://a.net
,而使用HTTPS(TCP/443)访问任何网站,网关会发回https://a.net
的ServerHello
包,此时:
- 一些浏览器提示”证书错误”,阻止用户继续访问
- 另一些(更聪明的)浏览器会提示WiFi需要登录,并询问是否跳转至登陆页面
我发现,此时访问https://a.net
的IP与用手机网路访问时一样,都属于CloudFlare。于是我做了一个尝试。
2.猜测
- 将Host Header不是
a.net
的HTTP无条件301到https://a.net
- 对HTTPS试图识别访问的主机名,如不是
a.net
,则充当TCP代理,将用户的ClientHello
发至https://a.net
,并返回https://a.net
的ServerHello
等后续数据包……
3.尝试
获取HTTPS所访问的主机名,方法大抵有两种:
- 通过TLS协议扩展中的
servername
字段(也称作SNI,或Server Name Indication) - 通过证书的
subjectAltName
(下简称SAN)
于是我试图构建一个HTTPS连接,但其具有如下特点:
- SNI扩展中的
servername
字段为a.net
Host
这一HTTP Header的值为hardrain980.com
openssl s_client -connect 45.63.22.104:443 -crlf -servername a.net
#出现交互界面后,构建HTTP请求
GET / HTTP/1.1
Host: hardrain980.com
Accept: */*
返回了我的博客首页的HTML。由此证明,该系统是通过TLS SNI扩展来识别HTTPS所请求的主机名,并根据此做出对应操作。
4.后记
- 似乎Stunnel能自定义SNI。Server配合后端,将其监听于TCP/443,Client模式下使用a.net做主机名或能绕过此系统。
- 此系统若通过证书来识别HTTPS主机名,自签名一个SAN包含
a.net
的证书或仍可绕过。 - 若此系统同时通过PKI检查证书有效性,则无解。
- 不明白此计费系统在未登录时为何不使用IP白名单,是因为CloudFlare CDN的IP会变化吗?
- 我付费使用该公司提供的网路,未使用信息技术谋取非法利益。
这网路的无线覆盖很垃圾,AP看起来是后安装的(墙壁上有走明线的管子),既没安在房顶上,也没放在靠中间的位置。奇怪的是网络信号5格却时常掉线,令我不得不使用USB网卡(XPS15没有RJ45端口)。