What Is a Unix Domain Socket? Permissions Explained
A Unix domain socket is local IPC between processes on one host. Learn how its file permissions control access and why world-writable sockets are risky.
A Unix domain socket is a local inter-process communication endpoint that lets two programs on the same host exchange data through the kernel, without using the network. On Linux, a socket bound to a filesystem path is protected by its file permissions: any process that can write to the socket file can connect to it. That makes socket permissions a real access control, and a world-writable socket owned by a root daemon is a direct path to root.
What is a Unix domain socket?
A Unix domain socket (AF_UNIX) is a communication endpoint for processes on the same machine. It uses the same socket API as TCP, but traffic never leaves the kernel, so it is fast and has no network exposure.
Databases, container runtimes, system managers and appliance daemons all use them. A management daemon running as root often listens on a Unix socket so that unprivileged tools can ask it to do privileged work. That design is safe only if the daemon controls who may connect and checks what they ask for.
The three types of Unix socket address
The Linux unix(7) manual page describes three kinds of address:
- Pathname sockets are bound to a file path with
bind(), for example/run/example.sock. They appear in the filesystem as a file of types. - Unnamed sockets have no name. The pair of sockets created by
socketpair()is unnamed, as is a stream socket that was never bound. - Abstract sockets use a name that starts with a null byte. They live in a separate namespace with no link to the filesystem.
The type matters for security because only pathname sockets have file permissions you can inspect and change.
How do Unix domain socket permissions work?
On Linux, connecting to a pathname stream socket requires write permission on the socket file, and the directory permissions along the path apply too. If the file mode grants write to "other", every local account can connect.
The unix(7) page adds two warnings. Portable programs should not rely on file permissions for socket security, because other Unix systems behave differently. And socket permissions have no meaning for abstract sockets: changing ownership or mode does nothing to who can reach them.
Why a world-writable socket is dangerous
A socket in mode 0777 accepts connections from any process on the host. If the program listening on it runs as root and trusts every caller, that program becomes a root shell for anyone with a local account.
That is the exact failure behind Check Point CVE-2026-123039. Gaia's dynamic_server process ran as root, listened on /tmp/dynamic_socket with mode 0777, did not authenticate connecting processes, and executed the command strings it received. Check Point's fix changed the socket to 0660, owned by root and the config group, and made the daemon reject unauthorized callers.
Two separate mistakes combined:
- Incorrect permission assignment (CWE-732). The file mode let everyone connect.
- Missing authorization (CWE-862). The daemon never checked who was on the other end.
Fixing either one would have blocked the attack. Fixing both is defense in depth.
How does a daemon check who is connecting?
Linux lets the listening side ask the kernel for the identity of the peer. The SO_PEERCRED socket option returns the credentials (process ID, user ID and group ID) of the process connected to a Unix stream socket. The kernel supplies the values, so the daemon does not have to trust anything the client says about itself.
For datagram sockets and message-level checks, the SCM_CREDENTIALS ancillary message carries the same credentials, once the receiver enables SO_PASSCRED. A daemon that runs privileged actions should check the peer UID against an allowlist on every connection and log rejections. The patched Gaia daemon does this and writes Rejected connection from unauthorized uid to its log.
Design rules for privileged socket services
If you run or write software that exposes a root service over a Unix socket, hold it to these rules:
- Restrictive mode. 0660 or tighter, with a dedicated group that contains only the accounts that need access.
- Private directory. Put the socket in a directory only the service and its clients can traverse, not a shared directory like
/tmp. - Peer authentication. Check
SO_PEERCREDon every connection; do not rely on the file mode alone. - No raw command execution. Accept a fixed set of operations with validated arguments, never a free-form command string.
- Logging. Record each request and each rejected caller, so incident responders have something to search.
How to check your own systems
Socket files show up in ls -l output with a leading s, for example srw-rw----. A leading srwxrwxrwx means world-writable. For a step-by-step sweep of a whole host, including how to map each socket to the process that owns it, follow our guide on how to find world-writable sockets on Linux.
For appliances where you cannot change the code, the risk lands differently. A local bug on a firewall is only one stolen login away from full control, which is why local privilege escalation on firewalls is urgent even when the CVSS vector says "local".