1. 程式人生 > >一文打盡端口複用 VS Haproxy埠複用

一文打盡端口複用 VS Haproxy埠複用

__出品|MS08067實驗室(www.ms08067.com)__ `本文作者:Spark(Ms08067內網安全小組成員)` ##1.概述   Haproxy是一個使用c語言開發的高效能負載均衡代理軟體,提供tcp和http的應用程式代理,免費、快速且可靠。   類似frp,使用一個配置檔案+一個server就可以執行。 優點: * 大型業務領域應用廣泛 * 支援四層代理(傳輸層)以及七層代理(應用層) * 支援acl(訪問控制列表),可靈活配置路由 * windows使用cygwin編譯後可執行(可跨平臺)   訪問控制列表(Access Control Lists,ACL)是應用在路由器介面的指令列表,這些指令列表用來告訴路由器哪些資料包可以接受,哪些資料包需要拒絕。 ##2.配置   官方配置手冊:   https://cbonte.github.io/haproxy-dconv/2.2/configuration.html   配置檔案由全域性配置和代理配置組成: 全域性配置(global): + 定義haproxy程序管理安全及效能相關的引數 代理設定(proxies): * defaults * 為其他配置段提供預設引數,預設配置引數可由下一個"defaults"重新設定 * **frontend** * 定義一系列監聽的套接字,這些套接字可接受客戶端請求並與之建立連線 * **backend** * 定義"後端"伺服器,前端代理伺服器將會把哭護短的請求排程至這些伺服器 * listen * 定義監聽的套接字和後端的伺服器,類似於將frontend和backend段放在一起 示例: ``` global defaults log global mode tcp option dontlognull timeout connect 5000 timeout client 50000 timeout server 50000 frontend main mode tcp bind *:8888 option forwardfor except 127.0.0.1 option forwardfor header X‐Real‐IP # 配置acl規則 acl is‐proxy‐now urlp_reg(proxy) ^(http|https|socks5)$ # 分發到對應的backend use_backend socks5 if is‐proxy‐now use_backend http backend socks5 mode tcp timeout server 1h server ss 127.0.0.1:50000 backend http mode tcp server http 127.0.0.1:80 ```   重點關注frontend和backend。   Frontend中需要編寫acl規則,配置轉發。比如,當http流量來的時候,轉發給web服務;當rdp流量來的時候,轉發給rdp服務。   Backend中需要編寫具體的操作,就是轉達到哪個目標的哪個埠。 ##3.思路 ###(1) 思路一(通用)   編寫acl規則,在四層(傳輸層)進行負載,根據協議型別進行分發,例如:遇到http流量傳送給http服務,遇到rdp傳送給rdp服務等。 ###(2) 思路二   編寫acl規則,在七層(應用層)進行負載,判斷應用型別進行分發,例如,遇到http分發到http服務,否則傳送到xxx服務。 ##4.步驟 以思路一為例: 1. 通過wireshark捕獲tpkt(應用層資料傳輸協議)資訊 2. 編寫acl規則路由進行流量分發 3. 新增後端server 4. 原始介面接管 5. 完成 ###4.1 捕獲tpkt   關於tpkt可百度或檢視參考連結   三次握手後,開始應用層資料傳輸。   使用wireshark抓包: ssh協議:
  前三個包為三次握手,第四個包的起始三位,便是我們需要的tpkt,例如ssh為535348。 rdp協議:030000 速查: | 協議 | TPKT | | ---- | ---- | | SSH | 535348 | | RDP | 030000 | | HTTP(GET) | 474554 | | HTTP(POS) | 504f53 | | HTTP(PUT) | 505554 | | HTTP(DEL) | 44454c | | HTTP(OPT) | 4f5054 | | HTTP(HEA) | 484541 | | HTTP(CON) | 434f4e | | HTTP(TRA) | 545241 | | HTTPS | 160301 | ###4.2 編寫acl規則 ``` global defaults timeout connect 5000 timeout client 50000 timeout server 50000 frontend main mode tcp bind *:8888 # 重點:編寫acl規則進行轉發 tcp‐request inspect‐delay 3s acl is_http req.payload(0,3) ‐m bin 474554 504f53 505554 44454c 4f5054 484541 434f4e 545241 acl is_ssh req.payload(0,3) ‐m bin 535348 acl is_rdp req.payload(0,3) ‐m bin 030000 # 設定四層允許通過 tcp‐request content accept if is_http tcp‐request content accept if is_ssh tcp‐request content accept if is_rdp tcp‐request content accept # 分發到對應的backend use_backend http if is_http use_backend ssh if is_ssh use_backend rdp if is_rdp use_backend socks5 backend socks5 mode tcp timeout server 1h server ss 127.0.0.1:50000 backend http mode tcp server http 127.0.0.1:80 backend ssh mode tcp server ssh 127.0.0.1:22 backend rdp mode tcp server rdp 192.168.213.129:3389 ```   該配置檔案的功能是監聽8888埠,將http流量(速查表中http協議的8種tpkt)轉發到本地的80上,將ssh流量轉發到本地的22埠上,將rdp流量轉發到另一主機的3389上。 ##5.實驗 * Target1:Ubuntu 16.04 x64 * IP:192.168.213.128 * 開啟22埠、80埠
* Target2:Win7 x64 * IP:192.168.213.129 * 開啟3389埠   啟動haproxy,-f 指定配置檔案,開啟8888埠表示啟動成功。-d:除錯模式,可不加。   HTTP協議:訪問靶機的8888埠,流量被haproxy分發至本機的80。   RDP協議:訪問靶機的8888埠,流量被haproxy分發至192.168.213.129的3389。   SSH協議:訪問靶機的8888埠,流量被haproxy分發至本機的22。   haproxy日誌: ##6.埠重定向   為了不影響正常的80埠的訪問,將過來的80埠流量轉發到8888埠上。這樣使用者正常訪問80埠時,流量會先轉發到8888埠上,再由haproxy轉發回80埠。 * Linux:iptables(不需要重啟服務) ``` iptables ‐t nat ‐A PREROUTING ‐i eth0 ‐p tcp ‐‐dport 80 ‐j REDIRECT ‐‐to‐port 8888 ```   訪問80可以正常訪問:
  Haproxy日誌有記錄,說明流量由80先到8888,再回到80。   Windows:netsh(需要重啟web服務) ``` netsh interface portproxy add v4tov4 listenport=80 connectport=8888 connectaddress=127.0.0.1 ``` **注意:如果在windows下啟用埠重定向,需要在埠啟動前新增netsh埠轉發規則。** ##7.參考連結 * https://www.cnblogs.com/readygood/p/9776403.html * https://blog.csdn.net/qq_28710983/article/details/82194404 * https://wenku.baidu.com/view/9f509844e2bd960591c67723.html?fr=search-1-wk_seaincome **轉載請聯絡作者並註明出