Networking in C · intermediate · ~15 min
Read and run a complete TCP server. It binds to 127.0.0.1, accepts one client, and echoes a single line back.
This lesson puts every piece together in order:
socket → setsockopt → bind → listen → accept → read/write → close
Each call has one job:
recv/send) move data over the connection.The server handles one connection, then exits. That keeps it small and predictable, which makes it ideal for labs and experiments.
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
#include <string.h>
#include <stdio.h>
int main(void) {
int srv = socket(AF_INET, SOCK_STREAM, 0);
int yes = 1; setsockopt(srv, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof yes);
struct sockaddr_in a; memset(&a, 0, sizeof a);
a.sin_family = AF_INET;
a.sin_port = htons(8080);
a.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
if (bind(srv, (struct sockaddr *)&a, sizeof a) < 0) { perror("bind"); return 1; }
if (listen(srv, 16) < 0) { perror("listen"); return 1; }
int client = accept(srv, NULL, NULL);
if (client < 0) { perror("accept"); return 1; }
char buf[256];
ssize_t n = recv(client, buf, sizeof buf - 1, 0);
if (n > 0) {
buf[n] = 0;
printf("server: got %s", buf);
send(client, buf, (size_t)n, 0); /* echo */
}
close(client);
close(srv);
return 0;
}
SO_REUSEADDR. Without it, your second run can fail with EADDRINUSE because the port is still held from the previous run.INADDR_ANY for a localhost lab. INADDR_ANY accepts traffic from any network interface. For a same-machine lab, use INADDR_LOOPBACK so only local (127.0.0.1) traffic can reach you.socket → setsockopt → bind → listen → accept → recv/send → close.close twice: once for the client socket, once for the listening socket.INADDR_LOOPBACK (local only) and SO_REUSEADDR (clean restarts).