wifidog 代碼簡單分析(1)

本文針對wifidog-20090925版本解釋下wifidog的代碼功能。
源碼包括wifidog網關協議src 文件夾以及自帶的libhttpd 庫libhttpd 文件夾(libhttpd庫用來創建wifidog 的http 服務,後面會提到這個庫具體做什麼),wifidog的配置文件wifidog.conf,這裏主要分析src 文件夾裏的源碼。

按照看源碼的習慣,在gateway.c main 裏的開始,按流程分析。
config_get_config()函數,是一個獲取全局變量config的函數,全局變量config 是關於網關全部配置的結構體,config 的成員變量都在wifidog.conf 文件裏,這個變量時貫穿全部流程的一個全局變量,要看懂主要的變量的作用。如下所說config 都是指這個全局變量config。

config_init()函數,設置config 成員的默認初始值,有些設置成NULL,詳細的看conf.c 的config_init函數,對照config 的結構體定義。

parse_commandline()函數,通過命令行獲取config 結構體的某些成員值,如wifidog -c /etc/wifidog.conf, 通過-c 設置configfile 的值。

config_read(),讀取configfile, 設置config 的成員值。這裏要注意,config_read會覆蓋parse_commandline 設置的config 成員值,parse_commandline會覆蓋config_init設置的config 成員值。

config_validate(),檢查config 的auth_server 和 gw_interface 值是否爲空,因爲這兩個變量值最爲重要。

client_list_init(), 這個函數涉及到另一個全局變量firstclient, 這個結構體主要保存客戶端的信息,如ip, mac, token, incoming, outgoing等,客戶端信息被存儲到一個鏈表裏,firstclient是鏈表頭。

init_signals(),處理一些信號,如quit 信號,會清理一些iptables 規則,殺掉ping 協議線程和counter 協議線程,前者是網關不斷髮ping 包給認證服務器證明自己是活的,後者是網關向認證服務器更新客戶端信息。

main_loop(),wifidog 流程開始。
首先檢查config 的 gw_address 和 gw_id 有沒有值,如果沒有值,通過get_iface_ip 和get_iface_mac 來獲取,這裏gw_id 設置成網關gw_interface 的mac 地址,gw_address 是網關 gw_interface 的IP,一般gw_interface 是br0, 在wifidog.conf 裏設置。

接着在網關 gw_interface 的IP 和 gw_port 上用libhttpd 庫運行一個http server,並創建對於文件'wifidog'、''、'about'、'auth'、'status'的訪問回調函數:http_callback_wifidog、http_callback_wifidog、http_callback_about、http_callback_auth以及http_callback_status,這裏所謂的訪問回調函數可以理解成當客戶端訪問auth 文件時會執行http_callback_auth函數,其他函數同理。

這裏還有一個libhttpd的函數,httpdAddC404Content,這個函數是用來處理客戶端第一次http 訪問外網時執行回調函數,回調函數就是這個函數的第二個參數http_callback_404。

對於上面四個訪問回調函數,我們下面會提到http_callback_auth,其餘三個不重要,這裏就不細說了。在此之前,我們先來看一下流程用到的第一個函數http_callback_404。

這裏需要有個場景:我們連上了一個路由器(等同於這裏的網關),這個路由器有wifigdog,並且綁定到了無線的interface 上,然後我們第一次上網,輸入url: www.baidu.com。

在http_callback_404函數裏,會把上述場景中的url 請求通過lihttpd 記錄下來,然後判斷認證服務器是否可達,接着就會把客戶端的瀏覽器重定向到認證服務器: http://auth_server/login/?gw_id=xxx&gw_address=xxx&gw_port=xxx&url=www.baidu.com
接着網關就是等待認證服務器重定向客戶端瀏覽器http://gatewayip:gatewayport/wifidog/auth?token=xxx, 這個token是認證服務器生成的,用來標識唯一客戶端。瀏覽器重新訪問網關,網關調用auth 的回調函數:http_callback_auth,這個函數就是拿着客戶端瀏覽器發送的token 去認證服務器上覈對token 的過程。

http_callback_auth(),該函數首先會檢查http 報文裏有沒有token,然後通過arp_get 拿該報文發送者的ip 對應的MAC 地址,然後到之前提到的客戶端鏈表裏搜此ip 和mac 對應的客戶端,如果搜不到,說明是新的客戶端接入,那麼就需要把它追加到鏈表裏;如果這個客戶端是logout請求(http報文請求裏有logout),那麼網關會發一個關於此客戶端下線的通知到認證服務器;如果不是logout請求,那麼不管是不是新的客戶端,都需要再次認證一下,這時交由函數authenticate_client 處理。

authenticate_client(),因爲我們之前已經把這個客戶端追加到鏈表裏了,所以首先去客戶端鏈表裏找,如果找得到這個客戶端,那麼就繼續進行。網關將此客戶端的mac、ip、token發送個login 請求到認證服務器[auth_server_request(&auth_response, REQUEST_TYPE_LOGIN, r->clientAddr, mac, token, 0, 0);],驗證此token 和之前認證服務器給客戶端的token 是否一致,如果一致會返回一個auth code=auth_allowed 給網關,通知網關對此客戶端放通,網關收到後會將此客戶端加入上網白名單(設置iptables 規則允許上網,客戶端不再看到訪問www.baidu.com 彈出非百度窗口),然後將客戶端重定向到http://auth_server/portal/?gw_id=xxx, 到此網關協議工作完成,但我們的源碼解析還沒有完成,下面回到http 幾個回調函數地方,接着講解。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章