QUIC所踩過的坑

2021-08-19 18:26:38 字數 1420 閱讀 4137

不靠譜的max data frame

- 當發包的位元組數到達服務端協商的上限時(flow control),服務端可以傳送乙個max *** data幀來允許客戶端擴大視窗。但是quic規定,不允許對ack-only packet進行相應,這意味著如果max *** data 幀丟失,並且後面所有包都是ack only packet。客戶端只能知道丟失了乙個包,但不能通過ack 告知server 端自己丟了包,那麼客戶端將會被阻塞住。

- 在很多實現上沒有實現對ack的追蹤(特別是ats)。如果出現大量的丟失ack情況,會導致client端的大量偽重傳。quic自09開始,需要追蹤對包含ack frame 的包的確認。並且建議隨機的傳送max data 或者ping來避免ack-only 包.11之後規定,ack應當包含已經確認過的舊的包,來避免ack丟失的情況的偽重傳。

- ack 的傳送時機在11之後的版本開始確立,在此之前,ack的傳送只有兩個策略,延遲傳送和每個包乙個ack。延遲傳送會導致恢復狀態過慢,每個包乙個ack很顯然發揮不了ack range 的優勢。如rfc5681,ack應該每隔2個滿packet(對應tcp的2 mss)傳送一次或者延遲25ms,這使得ack不至於過分延遲。並且亂序包應該更快的響應來加速恢復速度。

- 當我們在一次網路波動時丟失了多個包,那麼每個丟包都會把視窗減半,並且後續寶遵循快恢復演算法。很明顯這樣使得視窗一下次降低到乙個很小的值,並且恢復起來相當慢。自09以後引入recovery pos,使得避免因為一次網路波動而丟失多個包(此前ngtcp2 這裡有個bug導致排查了很久)。

- 當由於收到ack,而認定某個包丟失時。滑動視窗會減半(cwnd = bytes_in_flight / 2),這時很明顯bytes_in_flight > cwnd。這意味著傳送者不允許傳送任何資料,直到bytes_in_flight降到cwnd以下。這將會是乙個相當長的時間(目前尚未解決)。

- 在某些實現上rto重傳的2個packet,受到流控的控制。一旦rto發生當前bytes_in_flight必然大於cwnd, 這樣這兩個packet將會被阻塞到bytes_in_flight < cwnd。事實上很早以前的quic版本就規定rto傳送的2 packet不應該受到cwnd控制,這樣傳送出去的2packet,可以引出server端的ack以加速恢復速度。

- tcp有自己的一套pmtu探測演算法(rfc ***x 我忘了)。但是目前(基本上所有實現)的實現都沒有實現該演算法。這使得如果傳送的乙個包的位元組數大於當前路勁的mtu,那麼這個包將會被拆分成很多小的ip包,提高了某個quic包的丟失概率。

- 目前有不少網絡卡支援tso和tro,這使得tcp的分包更為簡單,快捷。但是quic沒有

- 實測過程中,內網環境中quic和tcp 測量出的rtt趨於相同分布。但是公網環境中tcp 80 比udp 4433 在高峰時測量出的rtt 快了10多倍(tcp 30-40ms quic 300-500ms)。這表明udp在公網傳輸比tcp慢很多。

git踩過的坑

4.git 修改當前的project的使用者名稱的命令為 git config user.name 你的目標使用者名稱 git 修改當前的project提交郵箱的命令為 git config user.email 你的目標郵箱名 如果你要修改當前全域性的使用者名稱和郵箱時,需要在上面的兩條命令中新增...

springboot踩過的坑

設定上下文路徑context path不生效 springboot 2.0之前的語法 server.context path xx 2.0之後的語法 server.servlet.context path xx 在配置yml時,報錯如下 caused by org.yaml.snakeyaml.sc...

SQL UNION踩過的坑

union 操作符用於合併兩個或多個 select 語句的結果集。請注意,union 內部的 select 語句必須擁有相同數量的列。列也必須擁有相似的資料型別。同時,每條 select 語句中的列的順序必須相同。select column name s from table name1 union...