2010-03-09 30 views
6

我想了解我得到的性能數字以及如何確定最佳線程數。TCP,HTTP和多線程Sweet Spot

看到這個職位的底部我的結果

我在下載頁面Perl寫的一個實驗性的多線程Web客戶端,抓住每個圖像標籤源並下載圖像 - 丟棄數據。

它使用一個非阻塞連接,每個文件的初始超時時間爲10秒,在每個超時後重試一次。它還緩存IP地址,因此每個線程只需執行一次DNS查找。

通過來自http://hubblesite.org/gallery/album/entire/npp/all/hires/true/的2.5Mbit連接,下載的總數據量爲1371個文件中的2271122個字節。縮略圖圖像由一家聲稱專門針對高帶寬應用的低延遲的公司託管。

牆時間爲:

1線程取4:48 - 0超時
2個線程取2:38 - 0超時
5線程需要2:22 - 20個超時
10個線程取2:27 - 40個超時
50個線程取2:27 - 170超時

在最壞的情況(50個線程)的CPU時間小於2秒被消耗b Ÿ客戶。

平均文件大小1.7K
平均RTT 100毫秒(如通過平測量)
平均CLI CPU /圖1毫秒

最快平均下載速度爲約15 KB/sec的整體5個線程。

服務器實際上似乎有相當低延遲時間,只需要218毫秒獲得每個圖像意味着只需要18平均毫秒的服務器來處理每一個請求:

0 CLI發送SYN
50個SRV垃圾車順
50 SRV發送SYN + ACK
100 CLI CONN建立/ CLI發送得到
150 SRV的recv的獲得
168 SRV讀取文件,發送數據時,調用close
218個CLI的recv HTTP報頭+完整的文件在2段nts MSS == 1448

我可以看到,每個文件的平均下載速度很低,因爲文件很小,並且每個文件的連接設置成本相對較高。

我不明白的是爲什麼我看不到2線程的性能改善。服務器似乎足夠快,但已經開始在5個線程上超時連接。

超時似乎後約900開始 - 我假設1000成功連接無論是5個或50個線程,可能是某種服務器上的限制閾值的,但我希望10個線程仍比2顯著快。

我在這裏錯過了什麼嗎?

EDIT-1

爲了便於比較我安裝的DownThemAll Firefox擴展,並用它下載的圖像。我將它設置爲4個併發連接,並有10秒的超時時間。 DTM花了大約3分鐘時間下載所有文件並將它們寫入磁盤,並且在大約900次連接之後,它也開始出現超時現象。

我將運行tcpdump來嘗試獲取tcp協議級別發生的更好的情況。

我還清除了Firefox的緩存並重新加載。 40秒重新加載頁面和所有圖像。這似乎太快 - 也許Firefox將它們保存在未清除的內存緩存中?所以我打開Opera並花了大約40秒。我假設他們更快,因爲他們必須使用HTTP/1.1流水線?

答案是!??

因此,經過多一點測試和編寫代碼來重新使用套接字通過流水線我發現了一些有趣的信息。

當以5個線程運行時,非流水線版本會在77秒內檢索前1026張圖像,但需要65秒才能檢索剩餘的290張圖像。這幾乎證實了MattH's有關我的客戶端受到SYN FLOOD事件影響的理論,導致服務器在短時間內停止響應我的連接嘗試。然而,這只是問題的一部分,因爲77秒的5線程獲得1026個圖像的速度仍然非常慢;如果您刪除了SYN FLOOD問題,則仍需要大約99秒才能檢索所有文件。所以基於一些研究和一些tcpdump的問題,似乎問題的另一部分是延遲和連接設置開銷。

下面是我們回到找到「甜蜜點」或最佳線程數問題的地方。我修改了客戶機來實現HTTP/1.1流水線,發現線程在這種情況下的最佳數量是15和20之間例如:

1線程取2:37 - 0超時
2線程取1:22 - 0超時
5線程取0:34 - 0超時
10個線程取0:20 - 0超時
11線程取0:19 - 0超時
15個線程取0 :16 - 0超時

影響這個因素有四個因素;延遲/ rtt,最大端到端帶寬,recv緩衝區大小 以及正在下載的圖像文件的大小。 See this site for a discussion on how receive buffer size and RTT latency affect available bandwidth

除了上述之外,平均文件大小會影響每個連接 傳輸速率的最大值。每次發出GET請求時,您都會在連接RTT的大小的傳輸管道上創建一個空白間隙 。例如,如果 你最大可能傳輸速率(recv的緩衝區大小/ RTT)爲2.5Mbit和 您的RTT爲100ms,那麼每一個GET請求招致你 管的最小32kB的差距。對於320kB的大平均圖像大小,相當於每個文件10%的開銷 ,有效地將可用帶寬降低到2.25Mbit。然而,對於 的爲3.2kb小平均文件大小的開銷跳轉到1000%和 可用帶寬被減小到232千比特/秒 - 約29KB。

因此,要找到最佳線程數:

間隙尺寸= MPTR * RTT
MPTR /(MPTR /缺口大小+ AVG文件大小)* AVG文件大小)

對於我上面的場景這給了我11個線程,這是非常接近我的現實世界的結果最佳的線程數。

如果實際連接速度是比理論MPTR那麼它應該 在計算替代地使用慢。

+1

你確定你的客戶端沒有限制自己到兩個併發的HTTP會話(導致客戶端#3等待客戶端#1 /#2完成)嗎?畢竟,這是一些HTTP RFC建議客戶應該做的。如果不是,你確定*服務器*(或者一路上)不這樣做? IE瀏覽器。你能驗證你的會話的同時性嗎? – bzlm 2010-03-09 15:59:36

+0

@bzlm:我從零開始寫客戶端,我沒有使用任何庫。所以我非常接近100%確定客戶端的連接是併發的。我想我可以通過tcpdump來查看我何時從服務器接收到SYN,儘管我不知道這是否足夠。 – 2010-03-09 16:12:13

+1

@hobbs:Perl線程怎麼會出問題?整個過程的CPU總時間不到2秒。 – 2010-03-09 16:13:05

回答

7

請糾正我,這個總結是不正確的:

  • multi-threaded客戶端將啓動連接到服務器的問題只是一個HTTP GET那麼線程關閉線程。
  • 當你說1,2,5,10,50個線程時,你只是指你允許多少個併發線程,每個線程本身只處理一個請求
  • 你的客戶端需要2到5分鐘才能下載1000圖像
  • Firefox和Opera會下載一個等效的數據在40秒內

設置我建議,服務器速率限制HTTP連接,或者通過服務器守護程序本身,服務器本地防火牆或最有可能專用防火牆。

實際上,濫用網絡服務的方式是不要將HTTP連接重複用於多個請求,並且您遇到的超時是因爲您的SYN FLOOD正在被鉗位。

Firefox和Opera可能正在使用的連接4-8下載的所有文件。

如果您重新設計代碼以重新使用連接,您應該達到類似的性能。

+0

@MattH:+1總的來說,我懷疑你對防火牆感知「SYN FLOOD」的超時是正確的。但是,由於兩個原因,我不同意你關於濫用的觀點。 HTTP/1.1標準**不要求客戶端支持持久連接。客戶可以選擇使用「連接:關閉」標題。其次,網站在單個網頁上列出所有1300多個縮略圖。如果您不準備通過非持久連接將多個圖像提供給單個客戶端,則將其分解爲多個頁面。我可能會嘗試持續連接。 – 2010-03-10 12:37:56

+0

@MattH:有一個由N個線程組成的線程池,每個線程一次只有一個TCP連接打開,用於N個併發的TCP連接。管道目前沒有使用,所以每個連接都用於下載一個文件。 – 2010-03-10 13:04:07

+0

@Robert:爲了濫用某些東西,你不必是惡意的。您不必成爲網絡分析師或服務器管理員就可以建立一個包含上千張圖片的網頁。 HTTP 1.1規範說實現'SHOULD'實現持久性。每分鐘打開一千個連接到網絡服務器效率不高(正如您在提出這個問題時發現的那樣)並且仍然是IMO濫用。您斷言「託管1300頁圖像」意味着「服務器必須支持來自單個主機的1300次同時連接嘗試」並不適用於任何服務器管理員。 – MattH 2010-03-10 17:09:44