Phase 1 · FOUNDATIONS
Networking 101 — IP, DNS, ports, curl
By the end of today
- Read an IP address and CIDR block, and name what /24 means
- Explain how DNS turns a name into an IP address
- Use curl -I and -v to walk the request path and debug it
How a name becomes a response: IP, DNS and ports
Type curl https://example.com and a surprising amount happens in the half-second before any text appears. Four things must line up: an address to reach, a name-to-address lookup, a port to knock on, and a request the other end understands. Learn those four and networking stops being magic.
Every machine on a network has an IP address — a number that says where it is. IPv4 writes it as four bytes separated by dots — 93.184.216.34 — each octet 0–255. Addresses come in blocks written in CIDR notation: 10.0.0.0/24 means “the first 24 bits are the network, the last 8 identify hosts,” which is 256 addresses from 10.0.0.0 to 10.0.0.255. A /16 fixes only 16 bits and leaves 65,536 addresses; the smaller the number after the slash, the bigger the block. You will read CIDR every single day — firewall rules, cloud subnets, and 0.0.0.0/0 (which means every address) all speak it.
An address gets you to the machine; a port gets you to the right program on it. One server runs many services, so each listens behind a numbered door: 80 for HTTP, 443 for HTTPS, 22 for SSH, 5432 for Postgres. So example.com:443 means “port 443 on that host.” Ports 0–1023 are the reserved, well-known ones.
But you typed a name, not a number, so first that name has to be resolved. DNS, the Domain Name System, is the internet’s phone book: it turns example.com into an IP. Your machine asks a resolver — often 1.1.1.1, Cloudflare’s public resolver, or one your network hands you — and the resolver walks the hierarchy (root, then .com, then example.com’s authoritative server) and returns the address, cached for a while so the next lookup is instant. The record type matters: an A record maps a name to an IPv4 address, AAAA to IPv6, and CNAME points one name at another.
Real world: Reaching a service is like phoning a large company. DNS is the directory that turns “Acme Corp” into a phone number — the IP. Dialling the main line reaches the building, but you still need an extension to land on the right desk, and that extension is the port. Dial a wrong number and nobody answers; get the extension wrong and you reach the wrong department entirely.
Put it together and you have the request path — the trip from a name to bytes on your screen:
curl is how you walk that path by hand. curl -I sends a HEAD request and prints only the response headers — the status line, content type, and any redirects — without downloading the body, which is perfect for “is it up, and what does it say?”. curl -v (verbose) narrates the whole trip: the IP it resolved and connected to, the TLS handshake, the request headers it sent, and the response headers that came back. When something is broken, -v shows which of the four steps failed — a DNS error, a refused connection, or a bad HTTP status — and that is the entire skill: knowing which link in the chain snapped.
Hands-On Lab
Budget about 25 minutes. Open your WSL2 Ubuntu 24.04 terminal (if you have not set up WSL2 yet, do Day 0 first — macOS and Linux users can follow along in their built-in terminal). You need a working internet connection; type each command and read every line of output.
# 1. What IP addresses does this machine hold? -brief keeps it to one line per interface.
ip -brief address
# Output (your addresses differ; note the /8 and /20 — that is CIDR on your own box):
# lo UNKNOWN 127.0.0.1/8 ::1/128
# eth0 UP 172.28.113.45/20 fe80::215:5dff:fe10:2a3c/64
# 2. Where does traffic leave for the wider internet? The default route names the gateway.
ip route
# Output (WSL2 uses a NAT gateway; the CIDR line describes your local subnet):
# default via 172.28.112.1 dev eth0 proto kernel
# 172.28.112.0/20 dev eth0 proto kernel scope link src 172.28.113.45
# 3. Which resolver will turn names into IPs for you? WSL2 generates this file automatically.
cat /etc/resolv.conf
# Output (the nameserver address depends on your WSL networking mode):
# # This file was automatically generated by WSL. ...
# nameserver 172.28.112.1
# 4. Resolve a name to an IP with no extra tools — getent uses the system resolver.
getent hosts example.com
# Output (the address you get will differ — DNS answers change and rotate):
# 23.215.0.136 example.com
# 5. Ask only "is it up, and what does it say?" — -I fetches headers, not the body.
curl -I https://example.com
# Output (date and etag vary; the 200 status line is what you are checking):
# HTTP/2 200
# content-type: text/html
# date: Fri, 10 Jul 2026 09:14:07 GMT
# 6. Ports and redirects: plain HTTP (port 80) to a site that forces HTTPS shows a 301.
curl -I http://github.com
# Output (the Location header points you at the HTTPS URL on port 443):
# HTTP/1.1 301 Moved Permanently
# Content-Length: 0
# Location: https://github.com/
# 7. Narrate the whole trip. -v prints to stderr; -o /dev/null drops the HTML body.
curl -sSv https://example.com -o /dev/null
# Output (trimmed — the connected IP will differ; read it top to bottom as the request path):
# * Trying 23.215.0.136:443...
# * Connected to example.com (23.215.0.136) port 443
# * using HTTP/2
# > GET / HTTP/2
# > Host: example.com
# > user-agent: curl/8.5.0
# >
# < HTTP/2 200
# < content-type: text/html
# 8. Prove the address+port you actually connected to, with curl's -w write-out template.
curl -s -o /dev/null -w '%{http_code} %{remote_ip}:%{remote_port}\n' https://example.com
# Output (status code, then the IP and port curl reached — again, the IP varies):
# 200 23.215.0.136:443
Read the path back out loud from the last two commands: a name became an IP (step 4), curl connected to that IP on port 443 (step 7), sent an HTTP request, and got a 200 back (step 8) — that is every arrow in the diagram, run by hand.
Common Errors & Fixes
These three catch almost everyone in their first week with curl and ip on Ubuntu 24.04. Read the error text slowly — learning to parse which step failed is the actual skill.
Common error: Fat-fingering the hostname — running
curl -I https://exmaple.com— prints:curl: (6) Could not resolve host: exmaple.comWhy:
curlnever got as far as connecting. It handed the name to the resolver, the resolver found no record forexmaple.com, and it came back empty. Error(6)is curl’s specific code for a DNS failure — the first link in the request path.Fix: Check the spelling, then confirm resolution independently with
getent hosts example.com. If a name you know is correct still fails, the problem is your resolver or/etc/resolv.conf, not the site.How you’d spot it in prod: “Could not resolve host” in a deploy log or app error usually means a typo in a config value, an internal DNS name that only resolves inside a VPC, or a resolver that is down. Verify the name resolves from the box that is actually failing, not from your laptop.
Common error: Hitting a closed port — running
curl -I http://localhost:8080when nothing listens there — prints:curl: (7) Failed to connect to localhost port 8080 after 0 ms: Connection refusedWhy: The host is right there —
localhostneeds no DNS — but nothing is bound to port8080, so the kernel answers the TCP handshake with an immediate RST and curl reports “Connection refused”. That is a fast, definite rejection: the machine is reachable and actively said “no one is home on that door.” It is the opposite of a firewall silently dropping packets, which leaves you hanging until a timeout. Error(7)is the connect step failing, one link further along than a DNS error.Fix: Use the port the service actually serves —
443for HTTPS,80for plain HTTP. If you own the box, check what is listening withss -tln(tomorrow’s tool). A refusal means “reached the host, wrong or closed door”; a hang/timeout more often means a firewall silently dropping packets.How you’d spot it in prod: “Connection refused” between two services almost always means the target process is not running or is bound to
127.0.0.1instead of0.0.0.0, or a security group blocks the port. Confirm the service is up and listening on the expected port before blaming the network.
Common error: Reaching for the old habit — running
ifconfigto see your IP on Ubuntu 24.04 — prints:Command 'ifconfig' not found, but can be installed with: sudo apt install net-toolsWhy:
ifconfig(andnetstat) ship in the legacynet-toolspackage, which Ubuntu no longer installs by default. The modern, always-present replacement is theipcommand fromiproute2.Fix: Use
ip address(orip -brief address) to see interfaces and IPs, andip routefor the routing table. Do not installnet-toolsout of habit — every current tutorial and runbook assumesip.How you’d spot it in prod: A script that calls
ifconfigwill fail on a fresh Ubuntu 24.04 host or a slim container image with “command not found”. The fix is to port the script toip, not to addnet-toolsto the image.
Networking Interview Questions
Cover the answers below and say your own version out loud first — trace the request path from name to response before you reveal each answer. Recalling before revealing is what makes these stick when an interviewer asks them cold. The four questions and answers render right after this note.
Go Deeper
Optional extras if you have ~30 more minutes today:
- 5 min — Run
man curland skim the-I,-v,-wand-Lflags; they are the four you will reach for most often. - 10 min — Read the Subnets and CIDR section of the Networking for DevOps guide for the bit-by-bit view of why
/24is 256 addresses and/16is 65,536. - 10 min — Play with prefix lengths in the CIDR checker and subnet calculator to watch the host count change as the slash moves.
- 5 min — Convert one IP between decimal, binary and hex in the IP address converter to see the four-bytes idea directly.
Walk me through what happens when you run curl https://example.com. Both
First the name is resolved: my machine asks a DNS resolver, which returns an IP address for example.com. curl opens a TCP connection to that IP on port 443, the HTTPS port. Over that connection it does a TLS handshake so the traffic is encrypted, then sends an HTTP request — a GET for the path plus a Host header. The server replies with a status line like HTTP/2 200, response headers, and the body. curl prints the body and the process exits. If I add -v, curl narrates each of those steps, so when something breaks I can see whether it was DNS, the connection, TLS, or the HTTP status that failed.
What is CIDR notation, and what does /24 mean? Both
CIDR — Classless Inter-Domain Routing — writes an IP range as an address plus a prefix length, like 10.0.0.0/24. The number after the slash is how many leading bits are fixed as the network part; the rest identify hosts. A /24 fixes 24 bits and leaves 8, so it covers 256 addresses, 10.0.0.0 to 10.0.0.255. A /16 fixes 16 bits — 65,536 addresses — and a /32 is a single host. The smaller the prefix number, the bigger the block. You read CIDR constantly in firewall rules, cloud subnets, and route tables, where 0.0.0.0/0 is shorthand for every address.
What is the difference between an IP address and a port? Both
An IP address identifies a machine on the network — it says which host to reach. A port identifies which program on that host you want, because one server usually runs many services at once. The IP gets your packet to the right building; the port gets it to the right desk inside. Ports are 16-bit numbers, 0 to 65535, and the well-known ones are worth memorising: 80 for HTTP, 443 for HTTPS, 22 for SSH, 5432 for Postgres. So 93.184.216.34:443 means port 443 on that host. If the host is up but nothing is listening on the port, you get connection refused rather than a timeout.
A teammate says 'the site is down.' How do you start debugging? Service
I narrow down which link in the chain broke instead of guessing. First, does the name resolve — a quick lookup, or curl -v to see the resolved IP; a 'could not resolve host' points at DNS. If it resolves, can I connect to the port — curl -v shows the connect succeeding or 'connection refused', which usually means the service is not listening or a firewall blocks it. If the connection is fine, what HTTP status comes back — a 200, a 500 from the app, or a 502 from a proxy tell very different stories. Working DNS then connection then TLS then HTTP, in order, turns 'it is down' into one specific failing step.
Mark Day 11 complete
Tomorrow you turn detective — ss, dig and ping become one repeatable flow for finding exactly where a connection breaks.
Stuck on today’s lab? Ask in Mission 90 Q&A