Networking I — TCP/IP, DNS, Sockets
A reliable byte stream is not a durable message protocol. A source-bounded lesson with worked reasoning, failure analysis and explicit runtime limitations.
Original publication date unrecordedUpdated
Lesson preparation & details
Level: intermediate
By the end, you should be able to
- Trace DNS, TCP, TLS and application acknowledgements through one request
- Implement bounded stream framing with short-read and EOF handling
- Diagnose socket states, DNS caching, retry budgets and resource ceilings
Bring with you
Sources checked: . A source check does not change the publication or update date.
Editorial review: · What review means
In this article · 33 sections
Why this session exists
An application can be running while name resolution, connection establishment, TLS, framing or a dependency deadline fails. “The network is slow” is not yet a diagnosis. Follow one request through the layers, then implement a protocol that remains correct when bytes arrive in inconvenient chunks. The lab executes against an in-memory transport; the complete loopback server/client adapter is a source-reviewed reference, not a server started during this review.
Prerequisites
Know sockets as file descriptors, HTTP request/response semantics and Python byte strings. Packet capture and live probing require authorization; the diagnostic output below is synthetic. You do not need root access or a cloud resource.
The postal model and its limits
IP resembles a sorting network: packets are forwarded toward destinations without a promise of delivery, ordering or uniqueness. TCP adds a reliable ordered byte-stream abstraction, congestion control and failure signaling. UDP preserves datagram boundaries but does not itself supply delivery, ordering or retransmission guarantees. DNS maps names to records; it is not a continuously live directory lookup.
A TCP acknowledgement concerns transport reception, not business success. A successful send reports bytes accepted for sending, which can be fewer than requested; sendall loops over sending but still does not prove that the receiving application processed or durably stored them. A timeout after a payment commit can therefore leave the caller uncertain. Request identity and application acknowledgements belong above TCP.
Protocol evolution, not one universal web path
DNS's foundational specifications are RFC 1034/1035 (1987); modern DNS also requires TCP support (RFC 7766, 2016). TCP's current consolidated specification is RFC 9293 (2022). TLS 1.3 is RFC 8446 (2018); QUIC is RFC 9000 (2021), and HTTP/3 uses QUIC rather than TCP. These standards explain the layers without claiming ARPANET was the first packet network, all clients use UDP DNS, or every request has the same handshake count.
Walk through curl, one chosen protocol path
Assume a cold DNS lookup, a new TCP connection, TLS 1.3 without early data, and HTTP/1.1. Real clients can reuse DNS/transport/TLS state, use a proxy, resolve locally, or select HTTP/2 or HTTP/3.
getaddrinfoconsults the configured name-service path. A stub resolver may ask a recursive resolver for A/AAAA records; the recursive server follows referrals if it lacks cached answers. DNS may use UDP, TCP, encrypted transports or a local cache according to configuration.- Routing chooses a next hop from the forwarding table. ARP for IPv4 or Neighbor Discovery for IPv6 can resolve local-link reachability. BGP helps exchange interdomain routes; it is not a fresh BGP query for each packet.
- The client sends SYN with initial sequence x. The server sends SYN-ACK with sequence y and acknowledgement x+1. The client sends ACK y+1. SYN consumes one sequence number in each direction. Client-side connection setup is approximately one RTT under this simplified no-loss path; the server receives the final ACK later.
- TLS negotiates keys and authenticates the peer under certificate/name trust rules. A new TLS 1.3 handshake typically adds one RTT before ordinary application data. Resumption/early data can change the exchange and bring replay constraints; never extrapolate one timing to every TLS version.
- HTTP sends the request and frames the response. A complete header is not necessarily a complete body. Persistent connections may remain open for reuse instead of closing after each response.
- When a TCP direction closes, FIN consumes a sequence number and is acknowledged. The peer's direction can remain open until it closes too. FINs/ACKs can combine; a diagram with two arrows is not automatically a complete four-message close trace.
Figure text equivalent — labels and relationships
- Participant “Client”.
- Participant “Configured resolver”.
- Participant “Server”.
- 1. solid: “Client” to “Configured resolver” — Name lookup if needed.
- 2. dotted: “Configured resolver” to “Client” — Address records with remaining TTL.
- 3. solid: “Client” to “Server” — SYN seq=x.
- 4. dotted: “Server” to “Client” — SYN-ACK seq=y ack=x+1.
- 5. solid: “Client” to “Server” — ACK ack=y+1.
- 6. solid: “Client” to “Server” — TLS 1.3 ClientHello.
- 7. dotted: “Server” to “Client” — Server handshake and authentication.
- 8. solid: “Client” to “Server” — Finished and HTTP request.
- 9. dotted: “Server” to “Client” — Framed HTTP response.
- 10. note: “Client” to “Server” — Connection can remain open for reuse (note placement over).
- 11. solid: “Client” to “Server” — FIN when client closes sending direction.
- 12. dotted: “Server” to “Client” — ACK.
- 13. dotted: “Server” to “Client” — FIN when server closes sending direction.
- 14. solid: “Client” to “Server” — ACK.
The layer cake and diagnostic tools
Application protocols include HTTP, DNS, SSH and SMTP. TCP/UDP transport sits above IP, which sits above link framing such as Ethernet/Wi-Fi; physical signaling carries those frames through media such as copper, fibre and radio. These labels are a debugging aid, not a claim that every implementation divides perfectly into the OSI model. TLS and QUIC cross simplistic boundaries.
Use curl -v for HTTP/TLS observations, ss for socket states/queues, an authorized tcpdump capture for packets, ip route for local forwarding, and ip neigh for neighbors. traceroute infers hops using limited-TTL probes and ICMP responses; its probes can be UDP, ICMP or TCP. A silent intermediate hop that still forwards later traffic is not proof of a broken link. Control-plane rate limiting and return paths affect visibility.
Read synthetic diagnostic output
Use ss -tanp to include listening and non-listening TCP sockets; ss -tnp does not normally include listeners, so the old two-row example used the wrong option. These are invented teaching rows, not host observations:
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 127.0.0.1:9999 0.0.0.0:*
ESTAB 12 0 127.0.0.1:9999 127.0.0.1:54321
CLOSE-WAIT 0 0 127.0.0.1:9999 127.0.0.1:54322For the established stream, Recv-Q reflects data queued for the application to consume; a sustained queue can indicate that the reader is slow. Send-Q on an established TCP socket reflects unacknowledged outgoing data, not proof the remote application committed anything. Listening-socket queue columns describe pending/backlog state rather than payload bytes. The CLOSE-WAIT row indicates peer closure while local closure is still pending; one brief row is normal, persistent accumulation after completed requests warrants an ownership investigation. Process details may be unavailable without permission; missing users: information does not imply no owner.
An authorized packet capture might produce this simplified handshake, with relative sequence numbering disabled for clarity:
client.54321 > server.9999: Flags [S], seq 1000
server.9999 > client.54321: Flags [S.], seq 5000, ack 1001
client.54321 > server.9999: Flags [.], ack 5001
client.54321 > server.9999: Flags [P.], seq 1001:1006, ack 5001, length 5
server.9999 > client.54321: Flags [.], ack 1006The data line accounts for bytes 1001 through 1005; ACK 1006 means the next expected byte. PSH is not an application-message delimiter. Repeated sequence ranges may indicate retransmission, but packet loss in the capture or offload can complicate interpretation. For TLS, the captured application payload is normally encrypted records. A successful handshake narrows the fault below later TLS/HTTP work; repeated SYNs without a response suggest a reachability/listener/filter problem, not a proven root cause.
Finally, dig status NXDOMAIN is an explicit negative name answer, SERVFAIL is resolver/server failure, and a timeout is no answer within the tool's budget. Inspect the queried server and answer/authority sections before blaming the application's database. Combine these observations: DNS succeeds, TCP establishes, Recv-Q grows and the app never returns a response points toward application consumption/progress rather than proving DNS failure.
DNS: authoritative data, recursive work, cached copies
An authoritative server answers for a zone. A recursive resolver does the work of following root/TLD/zone referrals and caches data. The application normally asks its configured resolver rather than contacting every server itself. CNAME chains, referrals and cached delegations can alter the simple walk.
Figure text equivalent — labels and relationships
- Node “Application stub” (square).
- Node “Recursive resolver” (square).
- Node “Root referral” (square).
- Node “TLD referral” (square).
- Node “Zone authoritative answer” (square).
- Node “Cache with remaining TTL” (square).
- “Application stub” leads to “Recursive resolver”. Line: normal; ends: arrow point.
- “Recursive resolver” leads to “Root referral”. Line: normal; ends: arrow point.
- “Recursive resolver” leads to “TLD referral”. Line: normal; ends: arrow point.
- “Recursive resolver” leads to “Zone authoritative answer”. Line: normal; ends: arrow point.
- “Zone authoritative answer” leads to “Recursive resolver”. Line: normal; ends: arrow point.
- “Recursive resolver” leads to “Cache with remaining TTL”. Line: normal; ends: arrow point.
- “Cache with remaining TTL” leads to “Application stub”. Line: normal; ends: arrow point.
TTL limits how long a record may be reused under the normal freshness rules; caches may evict earlier. Negative answers have separate rules, and serve-stale extensions can affect failure behavior. It is inaccurate to say every update remains stale for at least a TTL or that all copies expire simultaneously.
Worked cutover: a resolver cached an old record at t=-1 with TTL 3600. Lowering the authoritative TTL to 60 at t=0 does not rewrite that copy; under ordinary expiry it remains usable until t=3599. A resolver without the old record can see the new answer immediately. Lower TTL in advance of planned cutovers and retain old endpoints long enough for the actual client/resolver behavior; changing DNS also does not terminate existing pooled connections.
Interpret an illustrative dig answer: api.example. 42 IN A 192.0.2.10 has 42 seconds of returned TTL, not evidence that the authoritative configuration is 42. Compare response flags, status, answer/referral records and the queried resolver. A timeout and NXDOMAIN are different failures. DNS over TCP is normal protocol behavior, not a sign that the resolver is broken.
Loss, ordering and two unrelated meanings of TTL
Suppose the next expected TCP byte is 1001. A segment containing bytes 1006–1010 arrives before bytes 1001–1005. The receiver can buffer the later bytes, but the ordinary byte-stream API cannot deliver them ahead of the gap; the cumulative next-byte ACK remains 1001. When the missing range arrives, contiguous delivery can advance to 1011. A retransmitted duplicate must not become a second copy in the application stream. This is transport head-of-line waiting, not application-message framing. Selective acknowledgements can report other received ranges without redefining the cumulative ACK.
Loss detection can use acknowledgement feedback or retransmission timers. A missing response at the application does not identify which packet, endpoint or queue failed. TCP retransmission can recover a lost segment without repeating an application operation; an application retry on another connection can repeat a committed operation. Those are different layers of retry.
IPv4 TTL in a packet header bounds forwarding lifetime: a forwarding router decrements it by at least one, and discards an expired packet under RFC 1812 §5.3.1. Its practical hop-limit role prevents indefinite loops; it is not a DNS-cache timer or an application deadline. A packet beginning with TTL 2 cannot be forwarded by three routers. Traceroute exploits expiry responses, subject to filtering and response rules. IPv6 calls the corresponding field Hop Limit.
A DNS record TTL, by contrast, is a cache reuse interval in seconds. Negative DNS caching also has a contract: NXDOMAIN means nonexistence of the name reached by the lookup (possibly a CNAME target rather than the original alias), whereas NODATA means no records of the requested type under the response's name/class context. Under RFC 2308 §3, an authoritative negative answer's SOA supplies a lifetime derived from the smaller of its own TTL and SOA MINIMUM. With values 900 and 300 seconds, the derived lifetime is 300, not 900. Resolver policy and later DNS extensions further qualify behavior. Do not relabel a timeout or SERVFAIL as a cached nonexistent name.
TLS protects a channel, not the whole business transaction
For certificate-based HTTPS, success requires the client's certificate-chain and intended-service-name checks, not just any encrypted connection to an IP. A proxy that terminates TLS sees the plaintext; proxy-to-backend protection and peer verification must be configured separately. TLS does not make ordinary DNS answers authentic, conceal all traffic metadata, or prove that an authenticated server stored a payment durably.
TLS 1.3 early data is a separate safety decision: RFC 8446 Appendix E.5 warns about replay, including duplicated side effects. A state-changing request needs an application replay policy; “encrypted” is not equivalent to “exactly once.” The earlier sequence deliberately excludes early data. No TLS handshake, attack or packet experiment was run here.
TCP versus UDP and port accounting
TCP delivers ordered bytes while the connection succeeds, or reports a failure eventually according to the active transport/application timeout mechanisms. It does not promise success across a permanently broken network. UDP delivers messages that may be lost, duplicated or reordered; a receiver buffer too small can truncate/discard excess datagram data under its API. “One send equals one complete recv” is therefore too broad.
Choose TCP when its stream semantics and ecosystem fit, then add application framing. Choose UDP when the protocol explicitly handles the desired reliability/latency tradeoff: DNS queries, time synchronization or real-time media are examples. QUIC builds reliable streams and congestion control over UDP. It avoids TCP's cross-stream transport head-of-line blocking, but a lost packet can still delay data on its affected stream and shared congestion resources matter. UDP alone is not an excuse to ignore congestion.
Ports are 16-bit fields. RFC 6335 distinguishes system ports 0–1023, user ports 1024–49151 and dynamic/private ports 49152–65535; port 0 is reserved. Familiar conventions include SSH 22, DNS 53, HTTP 80 and HTTPS 443, with the transport also part of the service identity. These ranges describe registration, not a promise of a specific OS ephemeral allocator. Linux's configured ip_local_port_range can differ from 49152–65535. Binding low ports depends on capabilities and namespace sysctls, not exclusively a root UID. A connection is distinguished by protocol and endpoint tuple; the same local port can appear in different peer tuples under appropriate rules. Do not convert a nominal 28,000-port range into a universal 28,000-connection ceiling.
Congestion, flow control and the bandwidth-delay product
Receive-window flow control protects the receiver; the congestion window limits outstanding data based on path feedback. A sender is constrained by both. Slow start probes capacity rather than starting at the link's maximum rate. Loss, delay and explicit congestion signals influence algorithms; acknowledgements are not the only possible signal. Reusing a connection can amortize handshake and ramp-up costs, but HTTP/2 does not beat multiple HTTP/1.1 connections for every workload.
For a simplified loss-free stream, a 64 KiB effective window over 100 ms RTT permits about 65536 / 0.1 = 655360 bytes/s, roughly 0.625 MiB/s. A 100 Mbit/s path at 100 ms needs about 12,500,000 * 0.1 = 1,250,000 bytes in flight to fill its bandwidth-delay product. CPU, packet loss, congestion policy and application production/consumption can lower achieved throughput. Parallel streams are an option, not a required cure for every WAN transfer.
Hands-on: a complete framed echo protocol
The old framed client expected a length header, but its server replied with the unframed bytes echo: . Interpreting echo as a 32-bit length produced a bogus large read. Both ends must implement the same protocol.
Our protocol uses a four-byte unsigned network-order length followed by that many bytes, with a 1024-byte maximum for each frame. Empty payloads are allowed. The echo service returns the same payload, keeping the maximum valid in both directions. A partial header/body followed by EOF is an error; EOF before a new header is clean end-of-stream. Deadline enforcement belongs to the transport adapter.
import struct
MAX_FRAME = 1024
def encode_frame(payload):
if len(payload) > MAX_FRAME:
raise ValueError('frame too large')
return struct.pack('!I', len(payload)) + payload
def recv_exact(stream, size, allow_clean_eof=False):
if not 0 <= size <= MAX_FRAME:
raise ValueError('invalid read size')
result = bytearray()
while len(result) < size:
chunk = stream.recv(size - len(result))
if not chunk:
if allow_clean_eof and not result:
return None
raise EOFError('truncated frame')
result.extend(chunk)
return bytes(result)
def read_frame(stream):
header = recv_exact(stream, 4, allow_clean_eof=True)
if header is None:
return None
length, = struct.unpack('!I', header)
if length > MAX_FRAME:
raise ValueError('frame too large')
return recv_exact(stream, length)
def echo_one(stream):
payload = read_frame(stream)
if payload is None:
return False
stream.sendall(encode_frame(payload))
return True
class MemoryStream:
def __init__(self, wire, chunks):
self.wire = bytearray(wire)
self.chunks = iter(chunks)
self.output = bytearray()
def recv(self, size):
take = min(size, next(self.chunks, size), len(self.wire))
data = bytes(self.wire[:take])
del self.wire[:take]
return data
def sendall(self, data):
self.output.extend(data)
for sizes in ([1] * 40, [2, 7, 1, 4], [4096]):
stream = MemoryStream(encode_frame(b'hello') + encode_frame(b''), sizes)
assert echo_one(stream) and echo_one(stream)
assert not echo_one(stream)
reply = MemoryStream(bytes(stream.output), [1] * 40)
assert read_frame(reply) == b'hello'
assert read_frame(reply) == b''
assert read_frame(reply) is None
for wire in (b'\x00', encode_frame(b'abc')[:-1]):
try:
read_frame(MemoryStream(wire, [1] * 20))
except EOFError:
pass
else:
raise AssertionError('truncation accepted')
try:
read_frame(MemoryStream(struct.pack('!I', MAX_FRAME + 1), [4]))
except ValueError:
pass
else:
raise AssertionError('oversize accepted')
assert 65536 / 0.1 == 655360
assert (1024 - 20) // 4 == 251
print('framing, EOF, bounds and capacity arithmetic: PASS')Anatomy and observations
encode_frame counts bytes, not Unicode characters. !I is a four-byte big-endian unsigned integer. recv_exact accumulates short reads and distinguishes clean EOF from truncation. read_frame validates the size before reading the body. echo_one uses the same wire format as the client. The memory transport deliberately splits headers and bodies; output assertions demonstrate correctness without hoping that a loopback run happens to fragment at a useful point.
The model omits actual TCP scheduling, TLS, socket timeouts and performance. It does not treat one call to recv(1024) as one message, nor use an unbounded allocation based on a peer-supplied length.
Loopback server and client reference
Append this adapter to the preceding file for a separately authorized local exercise. It serves one connection and at most four messages, binds only loopback, uses per-operation timeouts, and closes handles through context managers. Do not execute it as part of this review. Per-operation timeouts are not an end-to-end slow-client deadline; a production adapter also budgets total time and admission.
# Reference adapter, syntax reviewed but no sockets opened in this review.
import socket
import sys
HOST, PORT = '127.0.0.1', 9999
def serve_reference():
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as listener:
listener.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
listener.settimeout(5)
listener.bind((HOST, PORT))
listener.listen(1)
conn, _ = listener.accept()
with conn:
conn.settimeout(2)
for _ in range(4):
if not echo_one(conn):
break
def client_reference(messages):
with socket.create_connection((HOST, PORT), timeout=2) as conn:
conn.settimeout(2)
for message in messages[:4]:
payload = message.encode('utf-8')
conn.sendall(encode_frame(payload))
assert read_frame(conn) == payload
conn.shutdown(socket.SHUT_WR)
if __name__ == '__main__' and len(sys.argv) > 1:
if sys.argv[1] == 'server':
serve_reference()
elif sys.argv[1] == 'client':
client_reference(sys.argv[2:] or ['hello', 'world'])
else:
raise SystemExit('choose server or client')SO_REUSEADDR can help local rebinding under OS rules; it does not erase all TIME_WAIT state or solve outbound port exhaustion. listen(1) requests a pending-connection backlog subject to OS rules, not a limit on all established application work. Thread-per-connection is not necessary for this bounded reference. Production concurrency needs a separate admission/queue policy.
Production failure modes and safe diagnosis
- TIME_WAIT: normally the active closer retains protocol state for delayed-segment safety. Count tuple/state populations and creation rate before tuning. Reuse/pool connections and bound concurrency first; do not blindly alter global
tcp_tw_reuseor useSO_REUSEADDRas an outbound fix. TIME_WAIT state is not necessarily an open application FD. - Half-open/stale connections: a silent peer or firewall can leave each endpoint with stale beliefs. TCP keepalive must be enabled and tuned; Linux documents a default idle period of 7200 seconds when enabled, not a universal application deadline. Probes may preserve some middlebox state, but do not prove application progress. Use application heartbeats/deadlines and bounded pools.
- Nagle plus delayed ACK: small writes awaiting acknowledgements can interact with delayed ACK behavior and add latency. The delay is implementation/configuration-dependent, not always 200 ms and not present in every RPC library. Coalesce logical writes, measure a packet trace when authorized, and choose
TCP_NODELAYfor the specific latency/bandwidth tradeoff. - DNS cutover: lower TTL before a planned transition, examine caches and existing connections, and distinguish authoritative failure from resolver failure. Multiple DNS providers do not automatically remove shared network/configuration dependencies.
- FD/tuple ceiling: sockets consume descriptors plus buffers and app state. With the explicit 1024/20/four-descriptor assumptions the FD ceiling is 251 operations. Fifty thousand connections require measured memory, CPU, quotas, admission and dependency capacity—not one sysctl recipe.
A documented outage and two general failure scenarios
Meta's first-party 5 October 2021 account explains that a maintenance command disconnected backbone data centers, a safety audit bug failed to stop it, and DNS sites withdrew BGP advertisements when they could not communicate with the data centers. The DNS machines were still operational. Loss of normal internal tools complicated recovery; this is not evidence for every badge-reader or revenue claim in the old text. The lesson is to keep recovery access independent and test guards under failure, not to call any one DNS architecture universally safe.
A route leak can direct traffic toward an unintended/undersized path; longest-prefix forwarding, route filtering and origin validation address different aspects. RPKI origin validation does not validate every AS path or prevent every leak. A dependency overload plus synchronized retries can also congest internal services and obstruct the control plane used for repair. These are explicit generic failure scenarios replacing unsupported vendor-specific details, not claimed reproductions of Cloudflare/AWS incidents.
Timeouts, retries and budgets
A short timeout with aggressive retries may hide a single slow node but amplify an overload. A long timeout without retry avoids duplication but can exhaust the caller's pool. Propagate a remaining deadline through service calls and bound both attempt count and retry traffic. A timeout does not prove a write did not commit; retry only under operation-specific idempotency/deduplication rules. Add jitter and backoff, stop when the budget is exhausted, and avoid stacked independent retries at every layer. Long timeouts are not “impossible to get wrong.”
Recall and worked answers
1. Explain the handshake
SYN(x), SYN-ACK(y, x+1), ACK(y+1) synchronize sequence spaces. The client can complete its ordinary connection establishment after roughly one RTT in the no-loss case. This is transport establishment, not TLS authentication or application success.
2. Why framing?
TCP does not preserve send-call boundaries. Our client and server both read a bounded four-byte length then exactly that many bytes; short reads continue, EOF mid-frame fails. HTTP's blank line ends headers, not necessarily the body; full HTTP framing is more than a delimiter.
3. Why does lowering TTL not repair old caches immediately?
A cached 3600-second record obtained at t=-1 can remain usable to t=3599. A new 60-second TTL affects new answers, not the old stored copy. It can help newly querying resolvers, so “helps nobody” is too broad.
4. What does keepalive solve?
It can detect dead idle transport peers and may keep some middlebox mappings alive when its interval fits policy. It cannot prove the application is responsive or that a business operation finished. Use explicit application timeouts/heartbeats too.
5. UDP examples
Small DNS exchanges can use UDP, with TCP also required by modern DNS rules. QUIC implements reliable multiplexed streams above UDP. Voice/game protocols can choose deadline-sensitive loss handling, but must still control congestion and define their semantics.
6. TIME_WAIT diagnosis
Find which side actively closes and whether a burst of short connections or a specific tuple pool is exhausting capacity. Prefer reuse and bounded pools. Thousands of TIME_WAIT records alone are not proof of a fault or of a process descriptor leak.
7. Authoritative versus recursive
An authority serves zone data; a recursive resolver obtains and caches answers for clients. Meta's DNS withdrawal made authoritative service unreachable under its dependency check; it did not mean every DNS machine crashed.
8. Silent traceroute hop
A router may forward data while suppressing/rate-limiting ICMP responses. Later responding hops or successful application traffic refute a simplistic “hop 8 broke the path” conclusion. Probe type, return path and filtering all matter.
9. Why were recovery tools affected at Meta?
The first-party report describes disconnection of the backbone and loss of normal network/tool access, with security/access constraints slowing recovery. Do not infer a complete internal-tool dependency graph from a public report. Design an independently reachable, authorized recovery route and rehearse it.
10. Capacity stretch
With 20 reserved FDs and four per operation under a 1024 limit, the arithmetic upper bound is 251. Share log handles, pool database connections, bound concurrent requests, choose an I/O model and size memory/CPU; only then set appropriate process/system limits. An LB can pool connections but does not automatically make idle state disappear or guarantee 50,000 connections.
Explain-out-loud test
Trace name resolution through application acknowledgement, distinguish a socket send from a durable business result, and repair the original framed/unframed mismatch. For an outage, state the failing layer and a measurement that could disprove your hypothesis.
Where this connects next
L4 balancers distribute flows; L7 proxies can inspect HTTP requests. Caches/CDNs change which network trips happen. Concurrency design decides how waiting sockets consume resources, and observability must separate DNS/connect/TLS/server/body phases. Protocol diagrams are one chosen path, not a universal timing model.
Sources and execution boundary
Primary snapshots captured on 2026-10-08: RFC 9293, RFC 1035/7766, RFC 9000, RFC 8446, Linux tcp(7), Python 3.12 socket documentation and Meta's 2021 first-party account. The 2026-10-10 review replayed the saved primary passages, added RFC 1812/2308/6335 source captures, and checked the loss-ordering, TTL and TLS replay boundaries. Exact framing code and independent chunk/EOF oracles execute without a socket. Server/client adapters and diagnostic commands are references; no capture, scan, server, provider call or real network benchmark was run.
- TCP specification
- DNS records and DNS TCP requirements
- QUIC and TLS 1.3
- Linux TCP
- Python 3.12 sockets
- Meta: more details about the October 4 outage
Original resource trail and reading purpose
The original session allocated 60 minutes for intuition, visuals, practice, production reasoning and recall. Treat that as optional pacing, not a completion or diagnostic-speed guarantee. Read the mechanisms here before attempting separately authorized service work.
These original companion destinations are retained for discovery, not used as reviewed claim evidence. Video identity, attribution, duration, playback and external reachability have not been verified in this pass; search links are searches, not specific videos. Historical promotional claims and inconsistent labels are not repeated as facts.
- Original video/search destination 1 — request-path orientation.
- Original video/search destination 2 — networking overview; original title/channel/description conflict.
- Original video/search destination 3 — socket-programming practice.
- Beej's Guide to Network Programming — socket API study.
- HTTP/3 — the past, present and future — HTTP/3/QUIC comparison.
- How Verizon and a BGP Optimizer knocked large parts of the internet offline — historical route-leak reading, not newly verified outage evidence.
For reviewed propositions use the primary sources above and the source-qualified mechanisms, not the optional resource labels. Previous: S060 OS basics. Next: S062 load balancers. Hub: The 6-Month Learning Plan. Navigation indicates a route, not acceptance of another lesson.
Pause / Recall / Apply
Can you explain it without the page?
Close the example. Reconstruct the core idea, then change one assumption. Mark complete when you’re ready; you can always undo it.
Stored in this browser only. No account, no sync. Clearing browser data removes your record.