한국어English日本語简体中文繁體中文DeutschไทยTiếng ViệtРусскийPortuguês (Brasil)EspañolBahasa Indonesia

Sách trắng lag game › Nguyên nhân gốc của truyền lại TCP

MTU black hole (chỉ gói lớn liên tục bị mất) PMTU black hole

ID nguyên nhân rt-mtu · Phụ trách chính Hạ tầng mạng (Đội hạ tầng) · Phối hợp Hạ tầng server (Đội hạ tầng), Phát triển server (Đội phát triển game)

Mở thẻ gốc có hình minh họa và thí nghiệm →

Khi kích thước tối đa mà một chặng giữa đường nhận được bị giảm đi nhưng thông báo “quá lớn” (ICMP) lại bị chặn, gói lớn gửi lại bao nhiêu lần cũng tiếp tục biến mất.

Vì sao Kích thước tối đa giảm ở chặng VPN hoặc tunnel, còn thông báo vượt kích thước bị tường lửa chặn → Dẫn đến Bên gửi không biết lý do nên cứ truyền lại cùng một gói lớn, RTO tăng gấp đôi sau mỗi lần → Trên màn hình Bình thường không sao, nhưng vào lúc có dữ liệu lớn đi qua (mở túi đồ, đến chỗ đông người, loading khi vào khu vực mới) thì cả các gói nhỏ phía sau cũng bị kẹt theo và game đứng hình, cuối cùng mất kết nối hoặc kẹt loading

Triệu chứng
Đứng hình, Mất kết nối, Không vào được·kẹt loading
Yếu tố
Mất gói
Ai gặp phải
Một khu vực hoặc nhà mạng, Chỉ mình tôi
Khi nào
Khi làm một thao tác nhất định, Ngay sau đăng nhập hoặc bảo trì
Phụ trách
Phụ trách chính Hạ tầng mạng (Đội hạ tầng) · Phối hợp Hạ tầng server (Đội hạ tầng), Phát triển server (Đội phát triển game)
Việc cần làm (Đội phát triển game)
Muốn tự hạ từ phía server thì đặt kích thước segment tối đa của socket (TCP_MAXSEG); chỉ chia nhỏ message trong code game thì không chặn được (TCP gom dữ liệu cần gửi lại theo kích thước MSS).
Việc cần làm (Đội hạ tầng)
Mạng: điều chỉnh MSS (clamping) ở thiết bị biên, cho phép ICMP báo vượt kích thước (type 3 code 4, fragmentation needed) trên tường lửa và network ACL của cloud. Thiết bị server·OS: cấu hình path MTU, kiểm tra tường lửa trên server và security group của cloud cũng không chặn ICMP báo vượt kích thước, dùng tcp_mtu_probing=1 của Linux làm lưới an toàn cuối cùng.
Con số tham khảo
Thường là 1.500 byte, đi qua tunnel thì còn khoảng 1.400. Cùng một gói bị truyền lại 5–6 lần thì thời gian đứng hình vượt quá 10 giây.
Trên đồ thị
Chỉ một phần cao · RTO và backoff theo từng kết nối, số lần mất kết nối theo khu vực hoặc nhà mạng
Chỗ cần xem
Các lần truyền lại của kết nối có vấn đề, qua bản bắt gói phía server hoặc bcc tcpretrans -s (hiển thị số thứ tự); xem mss, pmtu, backoff của kết nối đó bằng ss -ti. Từ server gửi tới địa chỉ người chơi đó một ping nhỏ và một ping 1.500 byte có bật DF (ping -M do -s 1472) rồi so sánh
Đúng nếu
gói đầy đúng kích thước MSS liên tục bị truyền lại với cùng số thứ tự, khoảng cách tăng gấp đôi mỗi lần, còn gói nhỏ hơn vẫn đi lại bình thường. Không có ICMP báo vượt kích thước (filter Wireshark icmp.type == 3 and icmp.code == 4), ping nhỏ có phản hồi nhưng ping lớn có DF thì mất hẳn, không phản hồi
Loại trừ nếu
gói nhỏ cũng biến mất theo → mất gói không liên quan kích thước (“Tràn hàng đợi ở điểm nghẽn”, “Đổi tuyến đường hoặc tuyến ECMP lỗi”). ICMP báo vượt kích thước có đến và pmtu trong ss -ti giảm xuống → cơ chế dò path MTU đang hoạt động đúng
Cách kiểm tra
Kiểm tra bằng công cụ hạ tầng (không cần code game)
Tìm hiểu thêm
tcp_mtu_probing=1 chỉ xác định là black hole và hạ MSS xuống 1.024 byte sau khi timeout truyền lại kéo dài vài giây (tương ứng tcp_retries1=3). Trong khoảng đó game đứng hình, nên chỉ coi đây là lưới an toàn cuối cùng; việc cần làm trước là điều chỉnh MSS để chặn từ đầu.

Nguồn

  1. RFC 1191: Path MTU discovery IETF
    Dò path MTU: gói quá lớn được báo bằng ICMP “fragmentation needed and DF set” (type 3 code 4)
  2. RFC 2923: TCP Problems with Path MTU Discovery IETF
    Vấn đề PMTU black hole: ICMP bị chặn nên chỉ gói lớn liên tục biến mất
  3. RFC 4821: Packetization Layer Path MTU Discovery IETF
    Cách tầng giao vận tự dò kích thước gói mà không cần ICMP (nền tảng của tcp_mtu_probing trên Linux)
  4. IP Sysctl Linux kernel
    tcp_mtu_probing: 0 là tắt, 1 là chỉ khi phát hiện black hole, 2 là luôn luôn (MSS khởi đầu là tcp_base_mss). tcp_retries1 mặc định 3
  5. net/ipv4/tcp_timer.c Linux kernel
    Khi truyền lại do RTO kéo dài đủ tcp_retries1 lần thì coi là đã phát hiện black hole, bật dò MTU để hạ MSS
  6. include/net/tcp.h Linux kernel
    TCP_BASE_MSS = 1.024 byte
  7. RFC 6298: Computing TCP's Retransmission Timer IETF
    Mỗi lần timer truyền lại hết hạn thì RTO tăng gấp đôi
  8. iptables-extensions(8) — Linux manual page netfilter
    TCPMSS --clamp-mss-to-pmtu: đi vòng qua vấn đề gói lớn bị kẹt do chặng chặn ICMP bằng cách điều chỉnh MSS trong SYN
  9. tcp(7) — Linux manual page Linux man-pages
    TCP_MAXSEG: kích thước segment tối đa của gói đi ra; đặt trước khi kết nối thì MSS báo cho phía bên kia cũng đổi theo
  10. Network maximum transmission unit (MTU) for your EC2 instance AWS
    Internet gateway và VPN có MTU 1.500; PMTUD cần ICMP type 3 code 4, nếu security group hoặc network ACL chặn thì không nhận được
  11. MTU considerations | Cloud VPN Google Cloud
    MTU của Cloud VPN gateway là 1.460 byte, MTU payload của tunnel IPv4 là 1.406 byte (đi qua tunnel thì còn khoảng 1.400)
  12. Demonstrations of tcpretrans, the Linux eBPF/bcc version IO Visor
    Hiển thị mỗi lần truyền lại trên một dòng, -s hiển thị kèm số thứ tự của gói đã truyền lại
  13. ss(8) — Linux manual page iproute2
    mss, pmtu (path MTU), backoff (số lần RTO đã tăng gấp đôi) trong ss -i
  14. ping(8) — Linux manual page iputils
    -M do bật DF và không gửi gói lớn hơn path MTU mà kernel biết; -s là kích thước dữ liệu (chưa tính 8 byte ICMP header)
  15. Display Filter Reference: Internet Control Message Protocol Wireshark
    Bộ lọc hiển thị icmp.type, icmp.code

Nguyên nhân nên xem cùng

Cùng tầng: Nguyên nhân gốc của truyền lại TCP

Nguyên nhân ở tầng khác gây cùng triệu chứng (Đứng hình)

Xem thẻ gốc có hình minh họa và thí nghiệm