Kiến thức nền
TCP/IP: Giao thức đã kết nối mọi thứ
Hai kỹ sư trong một sảnh khách sạn, một vấn đề không thể: làm cho bất kỳ mạng nào nói chuyện với bất kỳ mạng nào khác. Cách bài báo năm 1974 của Cerf và Kahn trở thành nền tảng của internet.
TL;DR
Đến năm 1973, ARPANET hoạt động — nhưng nó là một khu vườn có tường. Giao thức của nó, NCP, giả định một mạng duy nhất, đáng tin cậy không bao giờ mất gói. Thế giới thực có hàng chục mạng không tương thích, và không mạng nào có thể nói chuyện với nhau. Vint Cerf và Bob Kahn đã giải điều này trong một sảnh khách sạn: thiết kế một giao thức coi mọi mạng đều không đáng tin cậy và làm toàn bộ công việc khó ở các điểm cuối, không phải ở giữa. TCP/IP trở thành ngôn ngữ phổ quát của internet. Ngày 1 tháng 1 năm 1983, ARPANET bật một công tắc và internet hiện đại ra đời.
Vấn đề Kahn mang đến Stanford
Mùa xuân năm 1973, Bob Kahn bước vào văn phòng của Vint Cerf tại Stanford với thứ anh gọi là “một vấn đề thảm khốc.”
ARPANET đã thành công. Nhưng nó chỉ là một mạng. Quân đội Mỹ giờ có các mạng vệ tinh, các mạng radio gói di động, và ARPANET — và không mạng nào có thể trao đổi dữ liệu. Mỗi mạng sử dụng kích thước gói khác nhau, lược đồ địa chỉ khác nhau, quy tắc xử lý lỗi khác nhau. Kết nối chúng qua các gateway chỉ làm vấn đề tệ hơn: mọi gateway phải hiểu mọi phương ngữ của mạng.
Kahn đã dành nhiều tháng suy nghĩ về điều này và có bốn yêu cầu:
- Mỗi mạng nên hoạt động nội bộ mà không cần thay đổi
- Nếu một gói không đến, nó nên được phát lại
- Các gateway không nên giữ trạng thái — nếu một cái hỏng, các gói đi đường khác
- Không nên có điều khiển toàn cục
Anh có các ràng buộc. Anh không có giải pháp. Anh cần một nhà lý thuyết.
Cerf là nhà lý thuyết đó.
Một sảnh khách sạn ở Palo Alto
Trong vài tuần tiếp theo, hai người gặp nhau ở bất cứ đâu có thể — văn phòng, quán cà phê, và hiệu quả nhất, sảnh của Rickey’s Hyatt House ở Palo Alto. Cerf phác các sơ đồ trên giấy ăn. Kahn tranh luận về các chế độ lỗi. Tuệ giác cốt lõi xuất hiện đơn giản một cách lừa dối:
Mạng thì ngu. Các điểm cuối thì thông minh.
Thay vì xây một mạng đáng tin cậy — yêu cầu mọi thiết bị ở giữa hợp tác — họ sẽ xây một mạng không đáng tin cậy và làm cho các điểm cuối chịu trách nhiệm phục hồi từ sự không đáng tin cậy đó. Các gateway (sau gọi là router) sẽ làm một việc: chuyển tiếp gói. Chúng sẽ không lưu trạng thái, không xác minh giao hàng, không làm gì ngoại trừ nhìn địa chỉ đích và gửi gói tiếp.
Điều này được biết đến là nguyên tắc đầu cuối đến đầu cuối: đặt trí thông minh ở các rìa, không ở lõi. Đó là một trong những quyết định thiết kế có hệ quả nhất trong lịch sử tin học.
Tháng 5 năm 1974, Cerf và Kahn xuất bản “A Protocol for Packet Network Intercommunication” trên IEEE Transactions on Communications. Nó mô tả một giao thức duy nhất — TCP — sẽ xử lý mọi thứ.
Sự tách: TCP trở thành TCP/IP
TCP ban đầu cố gắng làm quá nhiều. Nó xử lý địa chỉ (gói này đi đâu?), định tuyến (nó đến đó như thế nào?), và độ tin cậy (điều gì xảy ra nếu nó không đến?). Điều này ổn cho một bài báo nghiên cứu. Nó là cơn ác mộng cho triển khai.
Jon Postel — cùng RFC editor sau này sẽ điều hành các hệ thống đặt tên và đánh số của internet — phản đối. Đây là hai vấn đề cơ bản khác nhau:
- Định tuyến là mối quan tâm ở tầng mạng. Mọi gói cần một địa chỉ và một đường.
- Độ tin cậy là mối quan tâm ở tầng truyền. Chỉ một số ứng dụng cần giao hàng được đảm bảo.
Một luồng video trực tiếp có thể chịu được các gói bị rơi. Một email chuyển giao thì không. Nhúng độ tin cậy vào tầng mạng có nghĩa là video sẽ mang chi phí của giao hàng được đảm bảo dù nó muốn hay không.
Lập luận của Postel thắng. Năm 1978, TCP được tách thành hai:
- IP (Internet Protocol) — xử lý địa chỉ và định tuyến. Bắn-và-quên.
- TCP (Transmission Control Protocol) — nằm trên IP, thêm độ tin cậy.
Các ứng dụng cần tốc độ hơn độ tin cậy có thể sử dụng UDP (User Datagram Protocol) trực tiếp trên IP. Kết quả là một chiếc đồng hồ cát:
HTTP FTP SMTP DNS ... ← nhiều giao thức ứng dụng
╲ │ │ ╱
╲ │ │ ╱
┌────────────────┐
│ TCP │ UDP │ ← tầng truyền
├────────────────┤
│ IP │ ← eo hẹp
└────────────────┘
╱ │ │ ╲
╱ │ │ ╲
Wi-Fi Ethernet 4G ... ← nhiều công nghệ tầng liên kết
IP là eo hẹp. Mọi công nghệ liên kết dưới nó và mọi ứng dụng trên nó đều nói IP. Đây là lý do bạn có thể kiểm tra email qua Wi-Fi, Ethernet, hay di động — mạng không quan tâm. Ứng dụng không quan tâm. Cả hai đều nói IP.
IP: Mọi máy có một địa chỉ
IP phiên bản 4 cho mọi thiết bị trên internet một địa chỉ 32-bit — bốn số từ 0 đến 255, cách nhau bằng dấu chấm. 192.168.1.1. Router của bạn có một cái. Server host trang này có một cái. Năm 1974, 32 bit trông có vẻ đủ: 4,3 tỷ địa chỉ cho một hành tinh với 4 tỷ người.
(Không đủ. Nhưng đó là vấn đề của những năm 1990.)
Định tuyến IP hoạt động như thư bưu điện. Mỗi gói mang một địa chỉ đích. Các router không biết đường đi đầy đủ — chúng chỉ biết bước tiếp theo. Mỗi router chuyển gói về đích của nó dựa trên một bảng định tuyến, và gói tìm đường qua internet từng bước một.
Bạn → Router nhà → Router ISP → ... → Đích
"Tôi gửi "Tôi gửi
lên upstream" sang AS tiếp theo"
Các router hợp tác qua các giao thức như BGP (Border Gateway Protocol) để xây dựng và chia sẻ các bảng định tuyến này. Chúng không cần một bản đồ của toàn bộ internet — chúng chỉ cần biết bước tiếp theo. Đây là phi tập trung trong thực tế: không router trung tâm nào biết mọi thứ, nhưng các gói vẫn tìm đường.
TCP: Làm cho một mạng không đáng tin cậy trở nên đáng tin cậy
IP giao các gói theo nỗ lực tốt nhất. Chúng có thể đến không đúng thứ tự, bị trùng, hoặc biến mất hoàn toàn. Công việc của TCP là che giấu tất cả điều đó khỏi ứng dụng.
Trước khi hai máy trao đổi dữ liệu, TCP thiết lập một kết nối với một bắt tay ba bước:
Client Server
│ │
│──── SYN ────────────────>│ "Tôi muốn kết nối (seq=x)"
│ │
│<─── SYN-ACK ─────────────│ "OK, tôi sẵn sàng (seq=y, ack=x+1)"
│ │
│──── ACK ────────────────>│ "Tuyệt, đi thôi (ack=y+1)"
│ │
│═══════ dữ liệu chảy ═════│
Một khi đã kết nối, TCP đánh số mọi byte nó gửi. Người nhận gửi lại các xác nhận (ACK) cho mọi byte nó nhận. Nếu người gửi không nhận ACK kịp thời, nó phát lại. Người nhận sắp xếp lại các gói không đúng thứ tự. Các bản sao bị loại bỏ.
import socket
# Kết nối TCP — OS xử lý SYN/SYN-ACK/ACK, phát lại, sắp xếp
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
s.connect(("example.com", 80))
s.sendall(b"GET / HTTP/1.0\r\nHost: example.com\r\n\r\n")
response = s.recv(4096)
# UDP — IP thô, không bắt tay, không đảm bảo
with socket.socket(socket.AF_INET, socket.SOCK_DGRAM) as s:
s.sendto(b"ping", ("8.8.8.8", 53))
data, addr = s.recvfrom(512)
TCP cũng làm điều khiển luồng (không gửi nhanh hơn người nhận có thể xử lý) và điều khiển tắc nghẽn (không gửi nhanh hơn mạng có thể xử lý). Các thuật toán này — Nagle, Slow Start, CUBIC — vẫn đang được tinh chỉnh ngày nay. HTTP/3 hiện đại thay thế TCP bằng QUIC, một giao thức dựa trên UDP tùy chỉnh, một phần để thoát khỏi blocking đầu-dòng của TCP. Nhưng đó là lãnh thổ Era 5.
Ngày cờ: 1 tháng 1 năm 1983
Trong tám năm sau bài báo năm 1974, TCP/IP và NCP cùng tồn tại. Triển khai TCP/IP là tùy chọn. Sau đó Bộ Quốc phòng Mỹ làm nó bắt buộc — và đặt một thời hạn.
Ngày 1 tháng 1 năm 1983. Mọi máy trên ARPANET sẽ chuyển từ NCP sang TCP/IP đồng thời. Không có triển khai dần dần, không có thời kỳ tương thích ngược. Nếu máy của bạn không nói TCP/IP vào nửa đêm, nó bị ngắt khỏi mạng.
Các quản trị viên gọi nó là “ngày cờ”. Một số người nghĩ nó liều lĩnh. Nhưng nó hoạt động. ARPANET thức dậy vào ngày 1 tháng 1 nói một ngôn ngữ mới — cùng ngôn ngữ internet nói hôm nay.
4.2BSD Unix, phát hành năm 1983, xuất xưởng TCP/IP như một phần của hệ điều hành. Đột ngột bất kỳ máy Unix nào cũng có thể kết nối. Internet ngừng là một dự án nghiên cứu của chính phủ và bắt đầu là cơ sở hạ tầng.
TCP/IP đã làm đúng gì
Các quyết định thiết kế được đưa ra trong một sảnh khách sạn năm 1973 đã đứng vững năm mươi năm:
- Mạng ngu, điểm cuối thông minh — internet đã mở rộng đến hàng tỷ thiết bị vì các router không cần hiểu lưu lượng chúng chuyển tiếp
- Phân tầng — Wi-Fi thay thế Ethernet, IPv6 đang từ từ thay thế IPv4, QUIC đang thách thức TCP — tất cả mà không phá vỡ các ứng dụng
- Giao hàng nỗ lực-tốt-nhất — chấp nhận sự không đáng tin cậy ở tầng IP, thay vì giả vờ mạng đáng tin cậy, làm cho toàn bộ hệ thống trung thực hơn và bền vững hơn
- Các tiêu chuẩn mở — bất cứ ai cũng có thể triển khai TCP/IP. IBM không sở hữu nó. AT&T không sở hữu nó. Bất cứ ai có RFC đều có thể xây một stack tuân thủ.
Điều một nó không giải quyết: tên. Một địa chỉ IP như 192.0.2.1 không phải cách con người điều hướng. Không có cách nào gõ google.com và có ý nghĩa — mọi máy giữ một file hosts.txt cục bộ ánh xạ tên sang địa chỉ, được duy trì bởi một quản trị viên duy nhất tại Stanford. Đến năm 1983, file đó có hàng nghìn mục và được cập nhật hai lần một tuần. Nó không thể mở rộng.
Giải pháp là DNS — Domain Name System — một cơ sở dữ liệu phân tán, phân cấp dịch các tên người-đọc-được thành các địa chỉ IP. Đó là điểm dừng tiếp theo.