diff options
author | ngie <ngie@FreeBSD.org> | 2015-11-25 08:19:01 +0000 |
---|---|---|
committer | ngie <ngie@FreeBSD.org> | 2015-11-25 08:19:01 +0000 |
commit | 65f700c61c7cb7cf82a5f23c5b327700a13fe6db (patch) | |
tree | f9247d6d56ccebd8b033ebbdcbd3090bc7961c28 /lib/libc/stdio | |
parent | 4aff854e252d1261ea4b6a3810379b7870f68d4a (diff) | |
download | FreeBSD-src-65f700c61c7cb7cf82a5f23c5b327700a13fe6db.zip FreeBSD-src-65f700c61c7cb7cf82a5f23c5b327700a13fe6db.tar.gz |
MFC r264737:
Discussed with: jilles
r264737 (by jilles):
libc/stdio: Fail fdopen() on an execute-only fd.
An execute-only fd (opened with O_EXEC) allows neither read() nor write()
and is therefore incompatible with all stdio modes. Therefore, the [EINVAL]
error applies.
Also adjust the similar check in freopen() with a NULL path, even though
this checks an fd which is already from a FILE.
Diffstat (limited to 'lib/libc/stdio')
-rw-r--r-- | lib/libc/stdio/fdopen.c | 3 | ||||
-rw-r--r-- | lib/libc/stdio/freopen.c | 5 |
2 files changed, 5 insertions, 3 deletions
diff --git a/lib/libc/stdio/fdopen.c b/lib/libc/stdio/fdopen.c index e5d167a..fbe37e8 100644 --- a/lib/libc/stdio/fdopen.c +++ b/lib/libc/stdio/fdopen.c @@ -70,7 +70,8 @@ fdopen(int fd, const char *mode) /* Make sure the mode the user wants is a subset of the actual mode. */ if ((fdflags = _fcntl(fd, F_GETFL, 0)) < 0) return (NULL); - tmp = fdflags & O_ACCMODE; + /* Work around incorrect O_ACCMODE. */ + tmp = fdflags & (O_ACCMODE | O_EXEC); if (tmp != O_RDWR && (tmp != (oflags & O_ACCMODE))) { errno = EINVAL; return (NULL); diff --git a/lib/libc/stdio/freopen.c b/lib/libc/stdio/freopen.c index 58227fa..e0104c8 100644 --- a/lib/libc/stdio/freopen.c +++ b/lib/libc/stdio/freopen.c @@ -92,8 +92,9 @@ freopen(const char * __restrict file, const char * __restrict mode, errno = sverrno; return (NULL); } - if ((dflags & O_ACCMODE) != O_RDWR && (dflags & O_ACCMODE) != - (oflags & O_ACCMODE)) { + /* Work around incorrect O_ACCMODE. */ + if ((dflags & O_ACCMODE) != O_RDWR && + (dflags & (O_ACCMODE | O_EXEC)) != (oflags & O_ACCMODE)) { fclose(fp); FUNLOCKFILE(fp); errno = EBADF; |