freenode
Kernel & Low-Level

Kernel adds atomic mkdir-and-open via O_CREAT|O_DIRECTORY

open(2) can create a directory and return a pinning file descriptor in one step, closing a long-standing race when setting up directory trees.

Linux is gaining a way to create a directory and open it atomically in a single open(2) call. A patch series from Jori Koolstra redefines the O_CREAT|O_DIRECTORY flag combination so the kernel performs a mkdir and returns a pinning file descriptor to the new directory, something plain mkdir(2) never provided.

Without that API, programs that build directory trees always race: they create the directory, then open it to set ownership, mode, labels, ACLs, xattrs, or timestamps. In the gap, another process can replace the entry. Checking with fstat after the open only goes so far; a directory made by another process with the same credentials is indistinguishable from one the caller just created, so the caller cannot tell whether it owns the object it is about to configure.

The combination must also specify O_EXCL. Trailing symlinks are not followed, and an existing path entry yields EEXIST, matching O_CREAT|O_EXCL file creates. Filesystems that cannot offer the atomic guarantee refuse the call with EOPNOTSUPP up front. That list currently includes atomic-open-only filesystems, tracefs, ecryptfs, and apparmorfs. kernfs is being extended so cgroupfs can use the feature, a need Christian Brauner highlighted at LPC.

The work also tightens related VFS behavior. Write opens of directories are rejected early as ENOTDIR rather than after a full path walk and possible create, and missing create or mkdir operations now report EOPNOTSUPP instead of the older mix of EACCES and EPERM. Some user-visible error codes therefore change. Selftests accompany the series to lock down the new contract.

Historically O_CREAT|O_DIRECTORY was either inconsistent or, since 2023, simply invalid (EINVAL). With three years of EINVAL in tree, the flags are free to take on the NetBSD-style atomic mkdir-and-open meaning.