Network · Section 2
socket(2)
Create an endpoint for communication and return a file descriptor referring to it.
Signature
#include <sys/socket.h>
int socket(int domain, int type, int protocol);- domain
- Protocol family: AF_INET, AF_INET6, AF_UNIX, AF_NETLINK, AF_PACKET, AF_VSOCK, AF_XDP, etc.
- type
- Semantics. SOCK_STREAM (reliable byte stream), SOCK_DGRAM (datagram), SOCK_RAW (raw IP), SOCK_SEQPACKET. OR with SOCK_CLOEXEC and/or SOCK_NONBLOCK to set those at create time (avoids the fcntl race).
- protocol
- Specific protocol within the family. 0 picks the default — TCP for SOCK_STREAM, UDP for SOCK_DGRAM. Non-zero for SOCK_RAW (the IP-layer protocol number) or for L2/L3-specific values.
Description
socket() creates a network communication endpoint and returns a file descriptor that subsequent calls (bind, connect, listen, accept, send, recv, sendto, recvfrom, shutdown, close) operate on. domain selects the protocol family — AF_INET / AF_INET6 for IP, AF_UNIX for local IPC, AF_NETLINK for kernel-to-userspace messaging, AF_PACKET for raw layer-2 frames, AF_VSOCK for hypervisor-guest channels. type selects the semantics (stream, datagram, raw, sequenced packet), optionally ORed with SOCK_CLOEXEC and SOCK_NONBLOCK. protocol picks a specific protocol within the family (0 for the default — TCP for SOCK_STREAM, UDP for SOCK_DGRAM). The returned fd is then configured and used like any other.
Architecture mapping
| Architecture | Number | ABI | Entry point |
|---|---|---|---|
| x86 (i386) | 359 | i386 | sys_socket |
| x64 (x86_64) | 41 | common | sys_socket |
| ARM64 (aarch64) | 198 | — | sys_socket |
Kernel history
Introduced in Linux 1.0.
1.0
socket() has been part of Linux since 1.0 with the BSD-style API; the original x86 syscall went through socketcall() (multiplexer), which is why i386 still has socketcall(102) in addition to socket(359).
2.6.27
SOCK_CLOEXEC and SOCK_NONBLOCK were added so callers could set those flags atomically at create time, closing race windows that previously required a separate fcntl(F_SETFD/F_SETFL).
3.4
AF_VSOCK was upstreamed to provide a host-guest channel that is independent of network configuration. Now widely used by container/VM tooling.
5.6
AF_XDP shipped to give userspace direct access to packet buffers via XDP, used for high-performance networking (DPDK alternatives, kernel-bypass with verified BPF).
seccomp & containers
Docker default profile
Allowed
Podman default profile
Allowed
socket() is allowed by Docker / Podman default profiles for the standard families. The strong hardening pattern is argument filtering: most workloads only need AF_INET, AF_INET6, AF_UNIX. Denying AF_NETLINK (configuration), AF_PACKET (sniffing), AF_VSOCK (host channels), and AF_XDP (kernel-bypass) removes an entire class of post-exploitation primitives without breaking application code. AppArmor and SELinux can complement this with type/peer restrictions, but seccomp is the cheapest start.
libseccomp
// Allow only TCP/UDP over IPv4/IPv6; deny AF_PACKET, AF_NETLINK, AF_VSOCK, etc.
for (int af : { AF_INET, AF_INET6, AF_UNIX }) {
seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(socket),
1, SCMP_A0(SCMP_CMP_EQ, af));
}
seccomp_rule_add(ctx, SCMP_ACT_ERRNO(EAFNOSUPPORT), SCMP_SYS(socket), 0);strace example
$ strace -e socket,connect curl -s https://example.com -o /dev/null
socket(AF_UNIX, SOCK_STREAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0) = 3
connect(3, {sa_family=AF_UNIX, sun_path="/run/nscd/socket"}, 110) = -1 ENOENT
socket(AF_INET6, SOCK_STREAM|SOCK_CLOEXEC|SOCK_NONBLOCK, IPPROTO_TCP) = 5
connect(5, {sa_family=AF_INET6, sin6_port=htons(443), sin6_addr=…}, 28) = 0strace decodes domain and type symbolically (AF_INET, SOCK_STREAM|SOCK_CLOEXEC). A useful trick for debugging connectivity: `strace -e network -yy program` shows the resolved address on each socket fd. To distinguish DNS, TCP, UDP, watch the sequence — DNS shows as UDP socket() + sendto() to port 53, then TCP socket() + connect() to the resolved IP.
Security & observability
socket() is the gateway to most network reconnaissance and exfiltration. AF_PACKET enables in-container sniffing (CAP_NET_RAW required, default-off in Docker) — alert if seen. AF_NETLINK is the path for processes to learn about every interface and route on the host; rootkits use it to discover the network layout before pivoting. The eBPF tracepoint sys_enter_socket captures domain/type/protocol; pair with /proc/<pid>/exe to identify the binary. For container forensics, comparing socket() families used vs the workload's expected protocol set is a useful baseline.
Errors
- EACCES
- Permission denied for the requested type/protocol (e.g. SOCK_RAW without CAP_NET_RAW).
- EAFNOSUPPORT
- The requested protocol family is not supported by this kernel or is filtered by seccomp.
- EINVAL
- —
- EMFILE
- Per-process file-descriptor limit reached.
- ENFILE
- System-wide file-table limit reached.
- ENOBUFS
- Insufficient kernel memory for the new socket structure (sk_buff cache exhaustion).
- ENOMEM
- —
- EPROTONOSUPPORT
- Protocol not supported within the requested family.
Flags
- AF_UNIX
- 1
- Local IPC over filesystem-named or abstract-namespace sockets. The fastest IPC available on Linux.
- AF_INET
- 2
- IPv4 sockets — TCP, UDP, ICMP. Still ~50% of internet traffic; do not assume v6-only.
- AF_INET6
- 10
- IPv6 sockets. With IPV6_V6ONLY=0 (the default) accepts both v4 and v6 connections, simplifying dual-stack servers.
- AF_NETLINK
- 16
- Kernel ↔ userspace control channel. Used by iproute2, audit, nfnetlink (firewall), and many subsystems for configuration.
- AF_PACKET
- 17
- Raw layer-2 frames. Required for tcpdump, dhclient, lldpd. Privileged (CAP_NET_RAW).
- AF_VSOCK
- 40
- Hypervisor-guest virtio communication. Used by Firecracker, qemu virtio-vsock; sometimes for sandbox-to-host RPC.
- AF_XDP
- 44
- —
- SOCK_STREAM
- 1
- Reliable, bidirectional, in-order byte stream. TCP for INET; SCTP also offers it.
- SOCK_DGRAM
- 2
- Unreliable, message-oriented. UDP for INET.
- SOCK_RAW
- 3
- —
- SOCK_SEQPACKET
- 5
- —
- SOCK_CLOEXEC
- 0x80000
- Set the close-on-exec flag at socket creation. Essential to prevent fd leaks across execve().
- SOCK_NONBLOCK
- 0x800
- Set the non-blocking flag at creation.