Understanding the Packet Flow
Understanding the Packet Flow
Let's zoom out for a second and see the whole journey your packet just took — from the ping command to the tcpdump output. This is your first complete mental model of a network exchange, and understanding it now will make the next modules much clearer.
The Complete Journey
When you typed:
docker compose exec client ping 10.10.0.4you triggered a whole chain of events that looks something like this:
[ ping command ]
↓
[ Client's ICMP module ]
↓
[ Client's IP layer ]
↓
[ Ethernet frame created ]
↓
[ Docker bridge (virtual switch) ]
↓
[ Stack container's Ethernet interface ]
↓
[ Stack container's IP + ICMP ]
↓
[ Echo reply generated ]
↓
[ Back through the bridge → client ]
Step-by-step breakdown
1. Ping creates an ICMP Echo Request
The client's kernel fills in an ICMP header, wraps it in an IP header, and then adds an Ethernet header. Each layer adds just enough information for the next hop to understand where the packet should go.
2. The client's ARP table gets involved
If the client doesn't already know the MAC address for 10.10.0.4, it first sends an ARP broadcast:
"Who has 10.10.0.4?"
The stack container replies with its MAC, so the client can address the Ethernet frame correctly.
3. The packet crosses the Docker bridge
Docker's internal bridge acts like a virtual Ethernet switch — it forwards the frame from the client's virtual interface (eth0) to the stack container's eth0.
4. The stack container's kernel receives the packet
Its IP layer reads the destination (10.10.0.4), sees it matches one of its own addresses, and hands it to ICMP.
5. ICMP replies
The stack's ICMP module builds an Echo Reply, swaps the source/destination fields, recalculates checksums, and hands it back down the stack to be transmitted.
6. The packet returns the same way in reverse
When you ran tcpdump on the stack side, you were listening right at the link layer — seeing each Ethernet frame arrive and depart.
Why This Matters
That's what makes this setup so powerful: you can capture traffic at any point in the stack and watch how headers get built, stripped, and rebuilt. From here on, every layer you implement will follow this same "up and down" journey.