rtld: ignore fstatfs(2) errors when checking MNT_NOEXEC flag

File descriptor we operate on might reference something that is not a
file, e.g. shmfd.  In this case, we cannot check MNT_NOEXEC in
principle.

If fstatfs(2) caused some failure on normal filesystem, then typical
expectation is that read or mmap of this file would also fail.  If not,
mmap(2) PROT_EXEC on MNT_NOEXEC filesystem returns EACCES.

Reported by:	obiwac@gmail.com
Sponsored by:	The FreeBSD Foundation
MFC after:	1 week
This commit is contained in:
Konstantin Belousov 2021-11-06 05:06:34 +02:00
parent 8363963a8f
commit c5637b8be8

View File

@ -2773,19 +2773,17 @@ do_load_object(int fd, const char *name, char *path, struct stat *sbp,
struct statfs fs;
/*
* but first, make sure that environment variables haven't been
* First, make sure that environment variables haven't been
* used to circumvent the noexec flag on a filesystem.
* We ignore fstatfs(2) failures, since fd might reference
* not a file, e.g. shmfd.
*/
if (dangerous_ld_env) {
if (fstatfs(fd, &fs) != 0) {
_rtld_error("Cannot fstatfs \"%s\"", printable_path(path));
return NULL;
}
if (fs.f_flags & MNT_NOEXEC) {
if (dangerous_ld_env && fstatfs(fd, &fs) == 0 &&
(fs.f_flags & MNT_NOEXEC) != 0) {
_rtld_error("Cannot execute objects on %s", fs.f_mntonname);
return NULL;
}
return (NULL);
}
dbg("loading \"%s\"", printable_path(path));
obj = map_object(fd, printable_path(path), sbp);
if (obj == NULL)