The Linux Programming Interface

(nextflipdebug5) #1

1022 Chapter 49


Modern x86-32 architectures provide hardware support for marking pages
tables as NX (no execute), and, since kernel 2.6.8, Linux makes use of this feature
to properly separate PROT_READ and PROT_EXEC permissions on Linux/x86-32.

Alignment restrictions specified in standards for offset and addr
SUSv3 specifies that the offset argument of mmap() must be page-aligned, and that the
addr argument must also be page-aligned if MAP_FIXED is specified. Linux conforms to
these requirements. However, it was later noted that the SUSv3 requirements differed
from earlier standards, which imposed looser requirements on these arguments.
The consequence of the SUSv3 wording was to (unnecessarily) render some for-
merly standards-conformant implementations nonconforming. SUSv4 returns to
the looser requirement:

z An implementation may require that offset be a multiple of the system page size.
z If MAP_FIXED is specified, then an implementation may require that addr be
page-aligned.
z If MAP_FIXED is specified, and addr is nonzero, then addr and offset shall have the
same remainder modulo the system page size.

A similar situation arose for the addr argument of mprotect(), msync(), and
munmap(). SUSv3 specified that this argument must be page-aligned. SUSv4
says that an implementation may require this argument to be page-aligned.

Example program
Listing 49-1 demonstrates the use of mmap() to create a private file mapping. This
program is a simple version of cat(1). It maps the (entire) file named in its command-
line argument, and then writes the contents of the mapping to standard output.

Listing 49-1: Using mmap() to create a private file mapping
–––––––––––––––––––––––––––––––––––––––––––––––––––––––––––– mmap/mmcat.c
#include <sys/mman.h>
#include <sys/stat.h>
#include <fcntl.h>
#include "tlpi_hdr.h"

int
main(int argc, char *argv[])
{
char *addr;
int fd;
struct stat sb;

if (argc != 2 || strcmp(argv[1], "--help") == 0)
usageErr("%s file\n", argv[0]);

fd = open(argv[1], O_RDONLY);
if (fd == -1)
errExit("open");
Free download pdf