1️⃣ What Is a Port?
A port is just a number (0–65535) that identifies a service on a machine.
Think of it like:
IP address → identifies the machine
Port → identifies the application inside the machine
Examples:
22 → SSH
80 → HTTP
443 → HTTPS
3306 → MySQL
When you see:
192.168.1.10:443
That means:
Machine IP = 192.168.1.10
Service = running on port 443
👉 A port by itself does NOT mean a connection exists.
It just means a process is listening.
2️⃣ What Is a Socket?
A socket is a full communication endpoint.
It includes:
IP address + Port + Protocol (TCP/UDP)
But a real TCP connection is uniquely identified by:
Source IP + Source Port + Destination IP + Destination Port + Protocol
Example:
Client: 10.0.0.5:51512
Server: 192.168.1.10:443
Protocol: TCP
That 5-tuple defines one unique connection.
So:
Port Socket
Just a number Full communication endpoint
Identifies a service Identifies a connection
Exists without traffic Exists during communication
3️⃣ How Is a Socket Created?
Sockets are created by the Operating System kernel, not directly by your application.
Applications only request them via system calls.
🔹 Client Side
When your browser connects to HTTPS:
Step 1 — socket()
Application asks kernel to create a socket.
Kernel:
Allocates socket structure in memory
Returns a file descriptor
Step 2 — connect()
Kernel:
Assigns an ephemeral port (e.g., 51512)
Initiates TCP 3-way handshake:
SYN
SYN-ACK
ACK
After handshake → connection becomes ESTABLISHED.
🔹 Server Side
When Nginx starts:
- socket()
Creates listening socket.
- bind()
Reserves port (e.g., 443).
- listen()
Marks socket as listening.
- accept()
When client connects:
Kernel creates a new socket
Listening socket stays open
One new socket per client
If 10,000 clients connect → 10,000 sockets.
4️⃣ Who Manages the Socket?
👉 The Linux kernel TCP/IP stack.
It manages:
TCP state (SYN_SENT, ESTABLISHED, TIME_WAIT)
Send/receive buffers
Sequence numbers
Congestion control
Memory allocation
Applications only:
Read
Write
Close
Everything else = kernel responsibility.
5️⃣ Why Does a Socket Use a File Descriptor?
Now the interesting part.
Sockets do not write to disk.
So why do they use file descriptors (FDs)?
Because in Unix/Linux:
“Everything is a file.”
This philosophy originated in early Unix at Bell Labs.
Linux treats:
Files
Sockets
Pipes
Terminals
Devices
epoll
eventfd
All as file descriptors.
6️⃣ What Is a File Descriptor Actually?
A file descriptor is:
Just an integer
Index into a per-process table
Points to a kernel object
Example:
0 → stdin
1 → stdout
2 → stderr
3 → first opened socket/file
When you call:
int fd = socket(AF_INET, SOCK_STREAM, 0);
Kernel:
Creates socket object
Stores it in process FD table
Returns a small integer
That integer is just a handle.
It does NOT mean disk file.
7️⃣ Why Reuse File Descriptor Mechanism?
Because it gives a unified API:
Same syscalls work for:
Files
Sockets
Pipes
Like:
read(fd)
write(fd)
close(fd)
poll(fd)
epoll(fd)
No special “network API” needed.
That abstraction is extremely powerful.
8️⃣ Why This Matters in Real Systems
In high-traffic systems:
50,000 concurrent connections
= 50,000 sockets
= 50,000 file descriptors
If you see:
Too many open files
It usually means:
You exhausted file descriptors
Not disk files
Check:
ulimit -n
Containers and Kubernetes pods share the node kernel, so:
Node FD limits matter
Socket exhaustion is real
TIME_WAIT floods can kill throughput
9️⃣ Visual Summary
Port
Just a service identifier
No active communication
Socket
Kernel object
Represents a live connection
Contains TCP state + buffers
File Descriptor
Integer handle
Points to kernel object
Used for unified I/O abstraction
10️⃣ Final Mental Model
Think of it like this:
IP = Building
Port = Door
Socket = Active phone call between two doors
File Descriptor = The call reference number your OS uses internally
Top comments (0)