Is mmap()
supposed to be able to create a write-only mapping of a O_WRONLY
opened file?
I am asking because following fails on a Linux 4.0.4 x86-64 system (strace
log):
mkdir("test", 0700) = 0
open("test/foo", O_WRONLY|O_CREAT, 0666) = 3
ftruncate(3, 11) = 0
mmap(NULL, 11, PROT_WRITE, MAP_SHARED, 3, 0) = -1 EACCES (Permission denied)
The errno
equals EACCESS
.
Replacing the open-flag O_WRONLY
with O_RDWR
yields a successful mapping.
The Linux mmap
man page documents the errno as:
EACCES A file descriptor refers to a non-regular file. Or a file map‐ ping was requested, but fd is not open for reading. Or MAP_SHARED was requested and PROT_WRITE is set, but fd is not open in read/write (O_RDWR) mode. Or PROT_WRITE is set, but the file is append-only.
Thus, that behaviour is documented with the second sentence.
But what is the reason behind it?
Is it allowed by POSIX?
Is it a kernel or a library limitation? (On a quick glance, I couldn't find anything obvious in Linux/mm/mmap.c
)
The IEEE Std 1003.1, 2004 Edition (POSIX.1 2004) appears to forbid it.
(emphasis added)
Also, on x86, it is not possible to have write-only memory, and this is a limitation of the page table entries. Pages may be marked read-only or read-write and independently may be executable or non-executable, but cannot be write-only. Moreover the man-page for
mprotect()
says:This being the case, you've opened a file descriptor without read access, but
mmap()
would be bypassing theO_WRONLY
by giving youPROT_READ
rights. Instead, it will refuse outright withEACCESS
.