<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    聶永的博客

    記錄工作/學習的點點滴滴。

    Fastsocket學習筆記之小結篇

    前言

    前面啰啰嗦嗦的幾篇文字,各個方面介紹了Fastsocket,盲人摸象一般,能力有限,還得繼續深入學習不是。這不,到了該小結收尾的時候了。

    緣起,內核已經成為瓶頸

    使用Linux作為服務器,在請求量很小的時候,是不用擔心其性能。但在海量的數據請求下,Linux內核在TCP/IP網絡處理方面,已經成為瓶頸。比如新浪在某臺HAProxy服務器上取樣,90%的CPU時間被內核占用,應用程序只能夠分配到較少的CPU時鐘周期的資源。

    經過Haproxy系統詳盡分析后,發現大部分CPU資源消耗在kernel里,并且在多核平臺下,kernel在網絡協議棧處理過程中存在著大量同步開銷。

    同時在多核上進行測試,HTTP CPS(Connection Per Second)吞吐量并沒有隨著CPU核數增加呈現線性增長:

    Image(2)

    內核3.9之前的Linux TCP調用

    Image(13)

    • kernel 3.9之前的tcp socket實現
    • bind系統調用會將socket和port進行綁定,并加入全局tcp_hashinfo的bhash鏈表中
    • 所有bind調用都會查詢這個bhash鏈表,如果port被占用,內核會導致bind失敗
    • listen則是根據用戶設置的隊列大小預先為tcp連接分配內存空間
    • 一個應用在同一個port上只能listen一次,那么也就只有一個隊列來保存已經建立的連接
    • nginx在listen之后會fork處多個worker,每個worker會繼承listen的socket,每個worker會創建一個epoll fd,并將listen fd和accept的新連接的fd加入epoll fd
    • 但是一旦新的連接到來,多個nginx worker只能排隊accept連接進行處理
    • 對于大量的短連接,accept顯然成為了一個瓶頸

    Linux網絡堆棧所存在問題

    • TCP處理&多核

      • 一個完整的TCP連接,中斷發生在一個CPU核上,但應用數據處理可能會在另外一個核上
      • 不同CPU核心處理,帶來了鎖競爭和CPU Cache Miss(波動不平衡)
      • 多個進程監聽一個TCP套接字,共享一個listen queue隊列
      • 用于連接管理全局哈希表格,存在資源競爭
      • epoll IO模型多進程對accept等待,驚群現象

    • Linux VFS的同步損耗嚴重

      • Socket被VFS管理
      • VFS對文件節點Inode和目錄Dentry有同步需求
      • SOCKET只需要在內存中存在即可,非嚴格意義上文件系統,不需要Inode和Dentry
      • 代碼層面略過不必須的常規鎖,但又保持了足夠的兼容性

    Fastsocket所作改進

    1. TCP單個連接完整處理做到了CPU本地化,避免了資源競爭
    2. 保持完整BSD socket API

    CPU之間不共享數據,并行化各自獨立處理TCP連接,也是其高效的主要原因。其架構圖可以看出其改進:

    20150205215656_12

    Fastsocket架構圖可以很清晰說明其大致結構,內核態和用戶態通過ioctl函數傳輸。記得netmap在重寫網卡驅動里面通過ioctl函數直接透傳到用戶態中,其更為高效,但沒有完整的TCP/IP網絡堆棧支持嘛。

    Fastsocket的TCP調用圖

    Image

    • 多個進程可以同時listen在同一個port上
    • 動態鏈接庫libfsocket.so攔截socket、bind、listen等系統調用并進入這個鏈接庫進行處理
    • 對于listen系統調用,fastsocket會記錄下這個fd,當應用通過epoll將這個fd加入到epoll fdset中時,libfsocket.so會通過ioctl為該進程clone listen fd關聯的socket、sock、file的系統資源
    • 內核模塊將clone的socket再次調用bind和listen
    • bind系統調用檢測到另外一個進程綁定到已經被綁定的port時,會進行相關檢查
    • 通過檢查sock將會被記錄到port相關聯的一個鏈表中,通過該鏈表可以知道所有bind同一個port的sock
    • 而sock是關聯到fd的,進程則持有fd,那么所有的資源就已經關聯到一起
    • 新的進程再次調用listen系統調用的時候,fastsocket內核會再次為其關聯的sock分配accept隊列
    • 結果是多個進程也就擁有了多個accept隊列,可避免cpu cache miss
    • fastsocket提供將每個listen和accept的進程綁定到用戶指定的CPU核
    • 如果用戶未指定,fastsocket將會為該進程默認綁定一個空閑的CPU核

    Fastsocket短連接性能

    在新浪測試中,在24核的安裝有Centos 6.5的服務器上,借助于Fastsocket,Nginx和HAProxy每秒處理連接數指標(connection/second)性能很驚人,分別增加290%和620%。這也證明了,Fastsocket帶來了TCP連接快速處理的能力。 除此之外,借助于硬件特性:

    • 借助于Intel超級線程,可以獲得另外20%的性能增長
    • HAProxy代理服務器借助于網卡Flow-Director特性支持,吞吐量可增加15%

    Fastsocket V1.0正式版從2014年3月份開始已經在新浪生產環境中使用,用作代理服務器,因此大家可以考慮是否可以采用。針對1.0版本,以下環境較為收益:

    • 服務器至少不少于8個CPU核心
    • 短連接被大量使用
    • CPU周期大部分消耗在網絡軟中斷和套接字系統調用上
    • 應用程序使用基于epoll的非阻塞IO
    • 應用程序使用多個進程單獨接受連接

    多線程嘛,就得需要參考示范應用所提供實踐建議了。

    Nginx測試服務器配置

    • nginx工作進程數量設置成CPU核數個
    • http keep-alive特性被禁用
    • 測試端http_load從nginx獲取64字節靜態文件,并發量為500*CPU核數
    • 啟用內存緩存靜態文件訪問,用于排除磁盤影響
    • 務必禁用accept_mutex(多核訪問accept產生鎖競爭,另fastsocket內核模塊為其去除了鎖競爭)

    從下表測試圖片中,可以看到:

    1. Fastsocket在24核服務器達到了475K Connection/Second,獲得了21倍的提升
    2. Centos 6.5在CPU核數增長到12核時并沒有呈現線性增長勢頭,反而在24核時下降到159k CPS
    3. Linux kernel 3.13在24核時獲得了近乎兩倍于Centos 6.5的吞吐量,283K CPS,但在12核后呈現出擴展性瓶頸

    HAProxy重要配置

    • 工作進程數量等同于CPU核數個
    • 需要啟用RFD(Receive Flow Deliver)
    • http keep-alive需要禁用
    • 測試端http_load并發量為500*CPU核數
    • 后端服務器響應外圍64個字節的消息

    測試結果中:

    • fastsocket呈現出了驚人的擴展性能
    • 24核,Linux kernel 3.13成績為139K CPS
    • 24核,Centos 6.5借助Fastsocket,獲得了370K CPS的吞吐量

    Fastsocket Throughput

    實際部署環境的成績

    Fastsocket Online

    8核服務器線上環境運行了24小時的成績,圖a展示了部署fastsocket之前CPU利用率,圖b為部署了fastsocekt之后的CPU利用率。 Fastsocket帶來的收益:

    • 每個CPU核心負載均衡
    • 平均CPU利用率降低10%
    • HAProxy處理能力增長85%

    20150205215658_398

    其實吧,這一塊期待新浪公布更多的數據。

    長連接的支持正在開發中

    長連接支持,還是需要等一等的。但是要支持什么類型長連接?百萬級別應用服務器類型,還是redis,可能是后者。雖然目前正做,但目前沒有時間表,但目前所做特性總結如下:

    1. 網絡堆棧的定制
      • SKB-Pool,每一CPU核對應一個預分配skb pool,替換內核緩沖區kernel slab
        • Percore skb pool
        • 合并skb頭部和數據
        • 本地Pool和重復循環使用的Pool(Flow-Director)
      • Fast-Epoll
        • 多進程之間TCP連接共享變得稀少
        • 在file結構體中保存Epoll entry,用以節省調用epoll_ctl時紅黑樹查詢的開銷
    2. 跨層的設計
      • Direct-TCP,數據包隸屬于已建立套接字會直接跳過路由過程
        • 記錄TCP套接字的輸入路由信息(Record input route information in TCP socket)
        • 直接查找網絡套接字在進入網絡堆棧之前(Lookup socket directly before network stack)
        • 從套接字讀取輸入路由信息(Read input route information from socket)
        • 標記數據包被路有過(Mark the packet as routed)
      • Receive-CPU-Selection 類似于RFS,但更輕巧、精準與快速
        • 把當前CPU核id編碼到套接字中(Application marks current CPU id in the socket)
        • 直接查詢套接字在進入網絡堆棧之前(Lookup socket directly before network stack)
        • 讀取套接字中包含的CPU核,然后發送給它(Read CPU id from socket and deliver accordingly)
      • RPS-Framework 數據包在進入網絡堆棧之前,讓開發者在內核模塊之外定制數據包投遞規則,擴充RPS功能

    Redis測試結果

    測試環境:

    • CPU: Intel E5 2640 v2 (6 core) * 2
    • NIC: Intel X520

    Redis配置選項:

    • TCP持久連接
    • 8個Redis實例,綁定不同端口
    • 使用到8個CPU核心,并且綁定CPU核

    測試結果:

    • 僅開啟RSS:20%的吞吐量增加
    • 啟用網卡Flow-Director特性:45%吞吐量增加

    但需要注意:

    • 僅為實驗測試階段
    • 為V1.0補充,Nginx和HAProxy同樣會收益

    Fastsocket v1.1

    V1.1版本要增加長連接的支持,那么類似于Redis的服務器應用程序就很受益了,因為沒有具體的時間表,只能夠慢慢等待了。

    以后一些優化措施

    1. 在上下文切換時,避免拷貝操作,Zero-Copy
    2. 中斷機制完善,減少中斷
    3. 支持批量提交,降低系統函數調用
    4. 提交到Linux kernel主分支上去
    5. HugeTLB/HugePage等

    Fastsocket和mTCP等簡單對比

    說是對比,其實是我從mTCP論文中摘取出來,增加了Fastsocket一欄,可以看出人們一直努力的腳步。

    Types Accept queue Conn. Locality Socket API Event Handling Packet I/O Application Mod- ification Kernel Modification
    PSIO ,
    DPDK ,
    PF RING ,
    netmap
    No TCP stack Batched No interface for transport layer No
    (NIC driver)
    Linux-2.6 Shared None BSD socket Syscalls Per packet Transparent No
    Linux-3.9 Per-core None BSD socket Syscalls Per packet Add option SO REUSEPORT No
    Affinity-Accept Per-core Yes BSD socket Syscalls Per packet Transparent Yes
    MegaPipe Per-core Yes lwsocket Batched syscalls Per packet Event model to completion I/O Yes
    FlexSC,VOS Shared None BSD socket Batched syscalls Per packet Change to use new API Yes
    mTCP Per-core Yes User-level socket Batched function calls Batched Socket API to mTCP API No
    (NIC driver)
    Fastsocket Per-core Yes BSD socket Ioctl + kernel calls Per packet Transparent No

    有一個大致的印象,也方便對比,但這只能是一個暫時的摘要而已,人類對性能的渴求總是朝著更好的方向發展著。

    部署嘗試

    怎么說呢,Fastsocket是為大家耳熟能詳服務器程序Nginx,HAProxy等而開發的。但若應用環境為大量的短連接,并且是小文件類型請求,不需要強制支持Keep-alive特性(短連接要的是快速請求-相應,然后關閉),那么管理員可以嘗試一下Fastsocket,至于部署策略,選擇性部署幾臺作為實驗看看結果。

    小結

    本系列到此算是告一段落啦。以后呢,自然是希望Fastsocket盡快發布對長連接的支持,還有更高性能的提升咯 :))

    資源引用

    posted on 2015-02-05 15:21 nieyong 閱讀(10454) 評論(5)  編輯  收藏 所屬分類: Socket

    評論

    # re: Fastsocket學習筆記之小結篇 2015-02-06 09:12 京山游俠

    太高大上了,370k的并發連接,猛。  回復  更多評論   

    # re: Fastsocket學習筆記之小結篇 2015-02-08 12:46 xanpeng

    "epoll IO模型多進程對accept等待,驚群現象"
    ——貌似2.6.32以后的內核就沒有驚群現象了吧  回復  更多評論   

    # re: Fastsocket學習筆記之小結篇 2015-02-09 09:40 nieyong

    @xanpeng
    在Linux內核版本 2.6.18 以前,所有監聽進程都會被喚醒,但是只有一個進程 accept 成功,其余失敗。這就是所謂的驚群效應 。在2.6.18 以后,已得到修復,僅有一個進程被喚醒并accept成功。  回復  更多評論   

    # re: Fastsocket學習筆記之小結篇 2015-10-05 16:22 computer_xu

    最后的那個表格 FastSocket 的Kernel Modification這一項應該是yes吧?看github上的代碼,有專門定制的2.6內核,還需要配合kernel模塊,再加上這個PRELOAD的so庫三個部分,才能跑起來。  回復  更多評論   

    # re: Fastsocket學習筆記之小結篇[未登錄] 2016-08-16 10:40 astrid

    你好,請問你是用什么方法或工具測試CPS的?
    最近在做這方面的工作,希望你能提供一些思路。非常感謝!  回復  更多評論   

    公告

    所有文章皆為原創,若轉載請標明出處,謝謝~

    新浪微博,歡迎關注:

    導航

    <2015年2月>
    25262728293031
    1234567
    891011121314
    15161718192021
    22232425262728
    1234567

    統計

    常用鏈接

    留言簿(58)

    隨筆分類(130)

    隨筆檔案(151)

    個人收藏

    最新隨筆

    搜索

    最新評論

    閱讀排行榜

    評論排行榜

    主站蜘蛛池模板: GOGOGO高清免费看韩国| 又粗又大又硬又爽的免费视频| 亚洲av无码成人影院一区| 久久亚洲精品成人综合| 亚洲第一页综合图片自拍| www.黄色免费网站| 日韩精品无码专区免费播放| 一区二区三区免费电影| 亚洲国产av玩弄放荡人妇| 亚洲综合色一区二区三区小说| 国产日产亚洲系列| 国产精品久久香蕉免费播放| 91情侣在线精品国产免费| 99re6在线精品视频免费播放 | 波多野结衣在线免费观看| 久久国产福利免费| 一级一黄在线观看视频免费| 老司机午夜精品视频在线观看免费| 亚洲 日韩 色 图网站| 亚洲春色在线观看| 久久精品国产亚洲AV大全| 亚洲av无码精品网站| 亚洲精品白浆高清久久久久久| 精品国产日韩亚洲一区| 亚洲国产精品无码久久青草| 亚洲成A人片在线观看无码3D | 亚洲an日韩专区在线| 亚洲黄色网址大全| 老色鬼久久亚洲AV综合| 国产成A人亚洲精V品无码| 国产精品亚洲A∨天堂不卡| a级亚洲片精品久久久久久久 | 亚洲精品美女久久久久久久| 一本色道久久综合亚洲精品蜜桃冫| 亚洲AV无码一区二区三区人| 亚洲国产福利精品一区二区| 久久久久se色偷偷亚洲精品av | 在线人成精品免费视频| 一区二区三区四区免费视频 | 亚洲av永久无码制服河南实里| 亚洲另类激情综合偷自拍图|