• <noscript id="ynq8u"></noscript>

    <s id="ynq8u"></s>
  • <strong id="ynq8u"></strong>

    <code id="ynq8u"><blockquote id="ynq8u"></blockquote></code>

    <small id="ynq8u"></small>
      1. 全國咨詢熱線:400-618-4000

        網絡攻防的藝術之TCP協議篇

        創建時間:2018年04月26日16時39分

        1、 概述

        網絡攻擊的主要內容包括系統安全攻防、網絡安全攻防、物理攻擊與社會工程學三部分: 系統安全攻防主要是利用軟件安全漏洞進行攻擊,網絡安全攻防利用協議棧的安全漏洞(不局限于此), 物理攻擊與社會工程學攻擊主要是利用人的心里弱點、物理設計缺陷。

        TCP(Transmission Control Protocol) 傳輸控制協議是TCP/IP協議棧的核心協議,它位于IP協議層之上,在網絡上的兩臺計算機之間提供可靠的、有序的通信通道。許多應用比如瀏覽器、SSH、Telnet、Email等使用TCP進行通信。TCP協議處于為應用提供主機到主機通信服務的傳輸層。

        一般我們講TCP提供可靠的有連接服務,這個可靠包括三層含義

        • 數據有序傳輸
        • 丟包重傳機制
        • 流量控制機制

        2、TCP協議的工作原理

        我們通過一個簡單的TCP client程序和TCP Server程序來展示TCP建立連接、數據傳輸、斷開連接的過程。以下這兩個程序中,為了能清晰說明程序的通信過程,不做容錯處理,力求簡單。工作當中這樣的程序是不能正常工作的。

        2.1 TCP Client 程序
        #include <stdio.h>
        #include <string.h>
        #include <errno.h>
        #include <sys/socket.h>
        #include <netinet/ip.h>
         
        #include <unistd.h>
        #include <sys/socket.h>
        #include <netinet/in.h>
        #include <arpa/inet.h>
        #define SER_ADDR "127.0.0.1"
        #define SER_PORT 9999
        //#define SER_ADDR "172.16.28.98"
         
        /* main function */
        int main(int argc, char *argv[])
        {
                /**
                 * Step 1: 創建一個socket, 指定SOCK_STREAM參數代表基于TCP協議
                 *   如果是UDP協議,則需要用SOCK_DGRAM
                 */
            int sockfd = socket(AF_INET, SOCK_STREAM, 0);
         
         
                /**
                 * Step 2: 設置目標主機IP地址和端口號
                 *   IP+Port, 標識網絡上某個主機的通信進程
                 */
            struct sockaddr_in dest;
            memset(&dest, 0, sizeof(struct sockaddr_in));
            dest.sin_family = AF_INET;
            dest.sin_addr.s_addr = inet_addr(SER_ADDR);
            dest.sin_port = htons(SER_PORT);
         
                /**
                 * Step 3: 連接服務器
                  */
            if (connect(sockfd, (struct sockaddr *)&dest,
                            sizeof(struct sockaddr_in)) != 0){
                        /* 此處SYN Flood攻擊會用到 */
                        fprintf(stdout, "Error for connect: %s\n", strerror(errno));
                        return 1;
                }
         
                /**
                 * Step 4: 向Server發送數據
                 */
         
                char *buffer1 = "Hello Server!\n";
            char *buffer2 = "Hello Again!\n";
            write(sockfd, buffer1, strlen(buffer1));
         
            write(sockfd, buffer2, strlen(buffer2));
         
                /**
                 *  Step 5: 關閉連接
                 */
            close(sockfd);
         
                return 0;
        }

        一個客戶端程序大概如下幾個步驟: 1. 創建一個socket,通過過指定參數SOCK_STREAM,來標識基于TCP傳輸, 如果需要用UDP協議的話,則需要指定SOCK_DGRAM. 特別指出,如果需要通過原始套接字進行通訊,需要指定SOCK_RAW。 2. 指定地址信息, 在網絡上,我們通過IP地址和Port來標識一個特定主機上的進程,此處填寫Server端的IP地址和端號。 3. 與Server建立連接, TCP是基于連接下協議,因此在數據傳輸之前,需要通過三次握手建立連接。 4. 收發數據, 一旦連接建立成功,C/S兩端就可以通過write/send/sendto/sendmsg發送數據,可以通過read/recv/recvfrom/recvmsg/接收數據 5. 關閉連接, 當數據收發完畢后,連接不在需要時,可以通過close斷開連接。

        2.2 TCP Server程序

        下面我們編寫一個TCP Server程序,還是老規矩,力求簡單,不做容錯處理
        #include <stdio.h>
        #include <string.h>
        #include <sys/socket.h>
        #include <netinet/ip.h>
        #include <unistd.h>
        #include <sys/types.h>
        #include <sys/socket.h>
         
        #define SER_ADDR 9999
         
        int main(int argc, char *argv[])
        {
            int sockfd, newsockfd;
            struct sockaddr_in my_addr, client_addr;
            char buffer[100];
         
                /**
                 * Step 1: 創建一個socket, 指定SOCK_STREAM代表TCP
                 */
            sockfd = socket(AF_INET, SOCK_STREAM, 0);
         
                /**
                 *  Step 2:   綁定一個端口號
                 */
            memset(&my_addr, 0, sizeof(struct sockaddr_in));
            my_addr.sin_family = AF_INET;
            my_addr.sin_port = htons(SER_ADDR);
            bind(sockfd, (struct sockaddr *)&my_addr, sizeof(struct sockaddr_in));
         
                /**
                 * Step 3: 監聽連接
                 */
            listen(sockfd, 5);
         
                fprintf(stdout, "Serve listenning....\n");
                while(1){
                        /**
                         * Step 4: Accept 一個連接請求
                         */
                        socklen_t client_len = sizeof(client_addr);
                        newsockfd = accept(sockfd, (struct sockaddr *)&client_addr, &client_len);
         
                        /**
                         * Step 5: 從當前連接讀取數據 */
                        memset(buffer, 0, sizeof(buffer));
                        int len = read(newsockfd, buffer, 100);
                        printf("Received %d bytes: %s", len, buffer);
         
                        /**
                         * Step 6: 關閉當前鏈接*/
                        close(newsockfd);
                }
         
                /**
                 * Step 7: 關閉套接字
                 */
                close(sockfd);
         
            return 0;
        }

        一個Server程序的大致步驟為:

        1. 創建一個socket

        2. 綁定一個端口號

        3. 開始監聽

        4. 接受一個連接請求。

        5. 收發數據

        6. 關閉連接請求

        7. 關閉socket

        其中 4、5、6可作為一個循環,多次響應連接請求。

        2. 3 掀開數據傳輸的面紗

        一旦連接建立, OS分別為Client端和Server端申請兩個Buffer, 一個是SendBuffer,用于發送數據,一個是ReceiveBuffer,用于接收數據。 TCP協議是全雙工的,兩端都可以發送和接收數據。詳細流程見下圖:

        這里面有幾個問題,我們此處并不會對TCP協議完整展開解釋,選取和我們后續課程相關重點的描述一下:

        1.TCP提供面向連接的服務, 連接的建立過程在下一章節中,重點描述。

        2.數據有序傳輸? 每個數據包編個序號,數據包到達主機可能錯序,在傳輸層調整順序后上傳。

        3.丟包重傳機制:引入滑動窗口機制, 窗口內的數據如果沒有接到應答ack, “超時”進行重傳

        4.流量控制機制:引入滑動窗口機制后,接收端實時通知發送端當前自己接受窗口大小,從而約束發送端的發送,進行流量控制

        TCP 部分一般稱之為Segment, 數據段, (補充: 在應用層--消息、傳輸層--數據段Segment、網絡層--包/分組 packet、 鏈路層--幀frame、 物理層bits),對于TCP header的格式如上圖所述, 詳細解讀如下:

        l 源端口號和目的端口號, 各占16bits

        l 32位序號 (seq)

        l 32位應答序號(ack)

        l TCP header長度: 4位, 以4字節度量, 故Header最長為64字節

        l 保留: 6位

        l 標志位: 6位, 包括 SYN、FIN、ACK、RST、PSH、URG

        l 滑動窗口: 16位, 可用于流量控制

        l 校驗: 16位

        l 緊急指針:16位, 當URG標志置位時, 此指針有效,用于帶外數據

        l 選項:0~320bits, 以32bits為單位,TCP可以通過options攜帶一些補充數據

        我們講,TCP是面向連接的服務, 因此就存在建立連接, 斷開連接等操作。后續我們選取針對連接建立過程和連接斷開過程進行攻擊方面的展示。

        3. TCP SYN Flood 攻擊

        3.1 TCP 建立連接(三次握手)

        我們說TCP提供面向連接的服務, 因此數據發送前需要先通過三次握手建立連接:

        1.第一次握手: 首先客戶端C(?)主動發起連接,發送SYN(連接請求標志), 以及序號SEQ=x(序號x隨機生成)到服務器端S。

        2.第二次握手: 服務器端S接受到SYN后, 向客戶端C也發送SYN及ACK, 且ack=x+1, 以及序號Seq=y(序號y隨機生成)。

        3.第三次握手: 客戶端接到SYN及ACK后, 核查ack是否為x+1, 若正確, 則客戶端C發送ACK 且ack=y+1,至服務器端S。

        4.服務器端S接收到ACK,核查ack是否為y+1. 若正確,則連接正常建立。

        三方握手建立連接的過程詳細見下圖

        3.2 SYN Flooding 攻擊

        在探討SYN攻擊之前,我們先看看linux內核對SYN是怎么處理的: 1. Server接收到SYN連接請求。 內部維護一個隊列(我們暫稱之半連接隊列,半連接并不準確), 發送ack及syn給Client端,等待Client端的ack應答,接收到則完成三次握手建立連接。 如果接收不到ack應答,則根據延時重傳規則繼續發送ack及syn給客戶段。

        利用上述特點。我們構造網絡包,源地址隨機構建,意味著當Server接到SYN包時,應答ack和syn時不會得到回應。在這種情況下, Server端,內核就會維持一個很大的隊列來管理這些半連接。 當半連接足夠多的時候,就會導致新來的正常連接請求得不到響應。 也就是所謂的DOS攻擊。

        詳細見下圖所示:

        3.3 SYN Flood 攻擊防護手段

        l tcp_max_syn_backlog: 半連接隊列長度

        l tcp_synack_retries: syn+ack 的重傳次數

        l tcp_syncookies : syn dookie

        一般的防御措施就是就是減小SYN+ACK重傳次數,增加半連接隊列長度,啟用syn cookie。不過在高強度攻擊面前,調優 tcp_syn_retries 和 tcp_max_syn_backlog 并不能解決根本問題,更有效的防御手段是激活 tcp_syncookies,在連接真正創建起來之前,它并不會立刻給請求分配數據區存儲連接狀態,而是通過構建一個帶簽名的序號來屏蔽偽造請求。

        傳智播客黑馬程序員C/C++與網絡攻防學科培養專項白帽子安全人才,課程包含 C語言開發實戰、C高級編程、C++核心編程與桌面應用開發、Linux高并發服務器開發、信息安全與企業應用開發、分布式云平臺開發、入侵檢測與網絡攻防等階段。

        黑馬程序員C/C++與網絡攻防課程關鍵技術點

        涉及到的熱門技術有:·

        Nginx(高并發反向代理服務器)

        ·GIT(分布式版本控制系統)

        ·Redis(NoSQL緩存數據庫)

        ·Memcache(key-value分布式緩存數據庫)

        ·Libevent(高并發反應堆模式API)

        ·Epoll(Linux內核高級多路IO技術)

        ·GDB(逆向工具)

        ·SHM(共享內存映射機制)

        ·VIM(文本編輯器)

        ·QT(跨平臺應用界面框架)

        涉及到的新興技術有:

        ·fastDFS(分布式文件系統)

        ·Golang(Google推出的開發編程語言)

        ·Docker(虛擬化容器技術)

        ·Go-micro(Go語言微服務框架)

        ·Beego(Go語言高性能web服務器框架)

        ·GEO(地理位置核心算法)

        ·ASN.1(跨平臺安全傳輸協議)

        ·RPC(遠程調用過程)

        ·Oracle(高級事務關系型數據庫)

        涉及到的網絡攻防技術有:

        ·Kali Linux(Hacker操作系統)

        ·Wireshark(網絡抓包分析工具)

        ·Aircrack-ng(可破解WEP/WPA/WPA2加密)

        ·AppScan(漏洞掃描工具)

        ·DDos(分布式拒絕服務攻擊)

        ·Web滲透(Web頁面代碼的攻擊形式)

        ·iptables(Linux內核防火墻技術)

        ·NetCat(網絡攻擊瑞士軍刀)

        ·TCPDump(Linux內核網絡協議捕捉器)

        ·SQLMAP(SQL注入漏洞攻防技能)

        本文版權歸傳智播客C/C++與網絡攻防學院所有,歡迎轉載,轉載請注明作者出處。謝謝!

        作者:傳智播客C/C++與網絡攻防培訓學院

        首發:http://c.itcast.cn/

        香蕉电影