OSDN Git Service

(split) LDP_man-pages: update original to v3.34.
[linuxjm/LDP_man-pages.git] / original / man2 / mprotect.2
1 .\" -*- nroff -*-
2 .\" Copyright (C) 2007 Michael Kerrisk <mtk.manpages@gmail.com>
3 .\" and Copyright (C) 1995 Michael Shields <shields@tembel.org>.
4 .\"
5 .\" Permission is granted to make and distribute verbatim copies of this
6 .\" manual provided the copyright notice and this permission notice are
7 .\" preserved on all copies.
8 .\"
9 .\" Permission is granted to copy and distribute modified versions of this
10 .\" manual under the conditions for verbatim copying, provided that the
11 .\" entire resulting derived work is distributed under the terms of a
12 .\" permission notice identical to this one.
13 .\"
14 .\" Since the Linux kernel and libraries are constantly changing, this
15 .\" manual page may be incorrect or out-of-date.  The author(s) assume no
16 .\" responsibility for errors or omissions, or for damages resulting from
17 .\" the use of the information contained herein.  The author(s) may not
18 .\" have taken the same level of care in the production of this manual,
19 .\" which is licensed free of charge, as they might when working
20 .\" professionally.
21 .\"
22 .\" Formatted or processed versions of this manual, if unaccompanied by
23 .\" the source, must acknowledge the copyright and author of this work.
24 .\"
25 .\" Modified 1996-10-22 by Eric S. Raymond <esr@thyrsus.com>
26 .\" Modified 1997-05-31 by Andries Brouwer <aeb@cwi.nl>
27 .\" Modified 2003-08-24 by Andries Brouwer <aeb@cwi.nl>
28 .\" Modified 2004-08-16 by Andi Kleen <ak@muc.de>
29 .\" 2007-06-02, mtk: Fairly substantial rewrites and additions, and
30 .\" a much improved example program.
31 .\"
32 .TH MPROTECT 2 2011-09-08 "Linux" "Linux Programmer's Manual"
33 .SH NAME
34 mprotect \- set protection on a region of memory
35 .SH SYNOPSIS
36 .nf
37 .B #include <sys/mman.h>
38 .sp
39 .BI "int mprotect(const void *" addr ", size_t " len ", int " prot );
40 .fi
41 .SH DESCRIPTION
42 .BR mprotect ()
43 changes protection for the calling process's memory page(s)
44 containing any part of the address range in the
45 interval [\fIaddr\fP,\ \fIaddr\fP+\fIlen\fP\-1].
46 .I addr
47 must be aligned to a page boundary.
48
49 If the calling process tries to access memory in a manner
50 that violates the protection, then the kernel generates a
51 .B SIGSEGV
52 signal for the process.
53 .PP
54 .I prot
55 is either
56 .B PROT_NONE
57 or a bitwise-or of the other values in the following list:
58 .TP 1.1i
59 .B PROT_NONE
60 The memory cannot be accessed at all.
61 .TP
62 .B PROT_READ
63 The memory can be read.
64 .TP
65 .B PROT_WRITE
66 The memory can be modified.
67 .TP
68 .B PROT_EXEC
69 The memory can be executed.
70 .\" FIXME
71 .\" Document PROT_GROWSUP and PROT_GROWSDOWN
72 .SH "RETURN VALUE"
73 On success,
74 .BR mprotect ()
75 returns zero.
76 On error, \-1 is returned, and
77 .I errno
78 is set appropriately.
79 .SH ERRORS
80 .TP
81 .B EACCES
82 The memory cannot be given the specified access.
83 This can happen, for example, if you
84 .BR mmap (2)
85 a file to which you have read-only access, then ask
86 .BR mprotect ()
87 to mark it
88 .BR PROT_WRITE .
89 .TP
90 .B EINVAL
91 \fIaddr\fP is not a valid pointer,
92 or not a multiple of the system page size.
93 .\" Or: both PROT_GROWSUP and PROT_GROWSDOWN were specified in 'prot'.
94 .TP
95 .B ENOMEM
96 Internal kernel structures could not be allocated.
97 .TP
98 .B ENOMEM
99 Addresses in the range
100 .RI [ addr ,
101 .IR addr + len \-1]
102 are invalid for the address space of the process,
103 or specify one or more pages that are not mapped.
104 (Before kernel 2.4.19, the error
105 .BR EFAULT
106 was incorrectly produced for these cases.)
107 .SH "CONFORMING TO"
108 SVr4, POSIX.1-2001.
109 .\" SVr4 defines an additional error
110 .\" code EAGAIN. The SVr4 error conditions don't map neatly onto Linux's.
111 POSIX says that the behavior of
112 .BR mprotect ()
113 is unspecified if it is applied to a region of memory that
114 was not obtained via
115 .BR mmap (2).
116 .SH NOTES
117 On Linux it is always permissible to call
118 .BR mprotect ()
119 on any address in a process's address space (except for the
120 kernel vsyscall area).
121 In particular it can be used
122 to change existing code mappings to be writable.
123
124 Whether
125 .B PROT_EXEC
126 has any effect different from
127 .B PROT_READ
128 is architecture- and kernel version-dependent.
129 On some hardware architectures (e.g., i386),
130 .B PROT_WRITE
131 implies
132 .BR PROT_READ .
133
134 POSIX.1-2001 says that an implementation may permit access
135 other than that specified in
136 .IR prot ,
137 but at a minimum can only allow write access if
138 .B PROT_WRITE
139 has been set, and must not allow any access if
140 .B PROT_NONE
141 has been set.
142 .SH EXAMPLE
143 .\" sigaction.2 refers to this example
144 .PP
145 The program below allocates four pages of memory, makes the third
146 of these pages read-only, and then executes a loop that walks upward
147 through the allocated region modifying bytes.
148
149 An example of what we might see when running the program is the
150 following:
151
152 .in +4n
153 .nf
154 .RB "$" " ./a.out"
155 Start of region:        0x804c000
156 Got SIGSEGV at address: 0x804e000
157 .fi
158 .in
159 .SS Program source
160 \&
161 .nf
162 #include <unistd.h>
163 #include <signal.h>
164 #include <stdio.h>
165 #include <malloc.h>
166 #include <stdlib.h>
167 #include <errno.h>
168 #include <sys/mman.h>
169
170 #define handle_error(msg) \\
171     do { perror(msg); exit(EXIT_FAILURE); } while (0)
172
173 char *buffer;
174
175 static void
176 handler(int sig, siginfo_t *si, void *unused)
177 {
178     printf("Got SIGSEGV at address: 0x%lx\\n",
179             (long) si\->si_addr);
180     exit(EXIT_FAILURE);
181 }
182
183 int
184 main(int argc, char *argv[])
185 {
186     char *p;
187     int pagesize;
188     struct sigaction sa;
189
190     sa.sa_flags = SA_SIGINFO;
191     sigemptyset(&sa.sa_mask);
192     sa.sa_sigaction = handler;
193     if (sigaction(SIGSEGV, &sa, NULL) == \-1)
194         handle_error("sigaction");
195
196     pagesize = sysconf(_SC_PAGE_SIZE);
197     if (pagesize == \-1)
198         handle_error("sysconf");
199
200     /* Allocate a buffer aligned on a page boundary;
201        initial protection is PROT_READ | PROT_WRITE */
202
203     buffer = memalign(pagesize, 4 * pagesize);
204     if (buffer == NULL)
205         handle_error("memalign");
206
207     printf("Start of region:        0x%lx\\n", (long) buffer);
208
209     if (mprotect(buffer + pagesize * 2, pagesize,
210                 PROT_READ) == \-1)
211         handle_error("mprotect");
212
213     for (p = buffer ; ; )
214         *(p++) = \(aqa\(aq;
215
216     printf("Loop completed\\n");     /* Should never happen */
217     exit(EXIT_SUCCESS);
218 }
219 .fi
220 .SH "SEE ALSO"
221 .BR mmap (2),
222 .BR sysconf (3)