It is currently just a toy script that post a table to a server, and the server address should be specified by the user. The intuition is very simple, I read the post request that I send to the server after manually typed in username and password, and I decide that do it automatically everytime you start the machine is more convinient.
However this is not that convinient, because very often when we connect to a wlan, we do not know whether it requires additional login steps to actually get connected to the outer Internet. Moreover, even when we know that it does, we can’t find where to type in our information, because the login web page may not pop out automatically, or they may take a while to pop out. In the current project, I assumed that the user has already known the login address, but what if he doesn’t? Wouldn’t it be better if we can automatically help him find the address and login for him?
Then the process can be divided into two steps:
1. Find the server address. 2. Post the login table.
The first step will largely depend on the method the wifi provider chooses to redirect you to the login page, or his method of Captive Portal. Currently there are two ways to do this.
When you send DNS packets, they rewrite the destination to their server, and provide you with their page. If you type in IP address instead of domain name, you will probably get a 404.
Take advantage of the redirect feature of HTTP to redirect your request to their server.
So which one does our school choose? Let’s find out.
I curled baidu.com with wireshark capturing the packets, these are the DNS packets between me (10.202.10.245) and the DNS servers (10.3.9.*):
The addresses given in the response are fraudulent: three of them are real baidu servers, but one of them (18.104.22.168) is not a baidu server.
Let’s capture HTTP packets now:
And this is the crucial step. My HTTP packets are sent to the fake server in the DNS response, and the fake server gave me a 302 code, redirecting me to another address, which should be the login page of the campus network.
However this cannot be the entire process. Because if they only use this simple trick, I can find several ways to evade it, like, directly type in real server IP. In this way I won’t send DNS query to the DNS server, so they have no chance to fraud me.
Obviously they have done some more sophisticated tricks in the lower layer, most likely transport layer, to completely block the visit to outer servers. Let’s see how this is done, by capturing all the TCP packets in a single “curl 22.214.171.124” process:
That’s the entire process. With basic knowledge of TCP protocol you can see through this image: TCP handshaking was successfully done, but then when we sent HTTP GET, the server responded with 302. Because 126.96.36.199 is a real baidu server, this shouldn’t have happened.
So, the trick is the router listens to all the 80 ports (HTTP) of connected devices, if the destination address is an outside address, the router fakes a 302 response, redirecting to the login page. Then it doesn’t matter much whether they’ve done anything in the DNS process or TCP handshaking process.