Index | Thread | Search

From:
"H. Hartzer" <h@hartzer.sh>
Subject:
Re: openat(2) is mostly useless, sadly
To:
"Theo de Raadt" <deraadt@openbsd.org>, <tech@openbsd.org>
Date:
Fri, 30 May 2025 18:16:09 +0000

Download raw body.

Thread
Theo de Raadt wrote:
> instead of requiring a programmer to put a flag on every system call acting
> upon the object.  Two operational flags are added, O_BELOW and F_BELOW.
>
> Creating such a locked directory fd is done with either
>
>      dirfd = open("path", O_DIRECTORY | O_BELOW);
>
> or you can lock a pre-existing dirfd:
>
>      fcntl(dirfd, F_BELOW);
>
> This dirfd has two charactistics.  Absolute accesses always fail with ENOENT.
> Relative accesses that attempt to traverse upwards fail with ENOENT.
> You can openat(dirfd, ".") but you cannot openat(dirfd, "..").
>
> Code using readdir() or similar must be careful because they will be provided
> with "." and ".." but operations on ".." will now fail.

I think that this is an excellent idea. It's very simple and should be
quite effective.

> RCS file: /cvs/src/sys/sys/fcntl.h,v
> diff -u -p -u -r1.22 fcntl.h
> --- sys/sys/fcntl.h	21 Jan 2019 18:09:21 -0000	1.22
> +++ sys/sys/fcntl.h	24 May 2025 00:33:56 -0000
> @@ -84,6 +84,7 @@
>  #define	O_ASYNC		0x0040		/* signal pgrp when data ready */
>  #define	O_FSYNC		0x0080		/* backwards compatibility */
>  #define	O_NOFOLLOW	0x0100		/* if path is a symlink, don't follow */
> +#define	O_BELOW		0x40000		/* openat(2) cannot open above */

I wanted to point out that the language can be confusing of "above",
"below", etc. Now it may be that this is named as appropriately as it
can be, but while I was reading my instinct was that "below" meant a
child directory, rather than a parent. I think there may be some
confusion over the semantics.

O_BELOW also sounds somewhat like it allows below, but not only below.
Maybe O_ONLYBELOW? Another possibility might be something like O_CHROOT,
which is a familiar and similar term, though might add other confusion.

I think that ascend/descend might be somewhat more intuitive terms.
Perhaps O_DESCEND, or O_ONLYDESCEND.

I'm looking forward to giving this a try.

-Henrich