]>
Commit | Line | Data |
---|---|---|
0b0ec758 | 1 | .\" Copyright (C) 2011 Christopher Yeoh <cyeoh@au1.ibm.com> |
7985dbf3 MK |
2 | .\" and Copyright (C) 2012 Mike Frysinger <vapier@gentoo.org> |
3 | .\" and Copyright (C) 2012 Michael Kerrisk <mtk.man-pages@gmail.com> | |
0b0ec758 | 4 | .\" |
5fbde956 | 5 | .\" SPDX-License-Identifier: Linux-man-pages-copyleft |
0b0ec758 | 6 | .\" |
7985dbf3 | 7 | .\" Commit fcf634098c00dd9cd247447368495f0b79be12d1 |
9bfc9cb1 | 8 | .\" |
4c1c5274 | 9 | .TH process_vm_readv 2 (date) "Linux man-pages (unreleased)" |
0b0ec758 | 10 | .SH NAME |
15f0b7af AC |
11 | process_vm_readv, process_vm_writev \- |
12 | transfer data between process address spaces | |
22294ea9 AC |
13 | .SH LIBRARY |
14 | Standard C library | |
8fc3b2cf | 15 | .RI ( libc ", " \-lc ) |
0b0ec758 | 16 | .SH SYNOPSIS |
7985dbf3 | 17 | .nf |
0b01869b | 18 | .B #include <sys/uio.h> |
dbfe9c70 | 19 | .PP |
0b0ec758 | 20 | .BI "ssize_t process_vm_readv(pid_t " pid , |
15d65653 MK |
21 | .BI " const struct iovec *" local_iov , |
22 | .BI " unsigned long " liovcnt , | |
23 | .BI " const struct iovec *" remote_iov , | |
24 | .BI " unsigned long " riovcnt , | |
25 | .BI " unsigned long " flags ");" | |
0b0ec758 | 26 | .BI "ssize_t process_vm_writev(pid_t " pid , |
15d65653 MK |
27 | .BI " const struct iovec *" local_iov , |
28 | .BI " unsigned long " liovcnt , | |
29 | .BI " const struct iovec *" remote_iov , | |
30 | .BI " unsigned long " riovcnt , | |
31 | .BI " unsigned long " flags ");" | |
7985dbf3 | 32 | .fi |
68e4db0a | 33 | .PP |
d39ad78f | 34 | .RS -4 |
a5111511 MK |
35 | Feature Test Macro Requirements for glibc (see |
36 | .BR feature_test_macros (7)): | |
d39ad78f | 37 | .RE |
68e4db0a | 38 | .PP |
a5111511 | 39 | .BR process_vm_readv (), |
4cd11c55 | 40 | .BR process_vm_writev (): |
9d2adbae MK |
41 | .nf |
42 | _GNU_SOURCE | |
43 | .fi | |
0b0ec758 | 44 | .SH DESCRIPTION |
7985dbf3 MK |
45 | These system calls transfer data between the address space |
46 | of the calling process ("the local process") and the process identified by | |
1ae6b2c7 | 47 | .I pid |
7985dbf3 MK |
48 | ("the remote process"). |
49 | The data moves directly between the address spaces of the two processes, | |
50 | without passing through kernel space. | |
efeece04 | 51 | .PP |
0b0ec758 MF |
52 | The |
53 | .BR process_vm_readv () | |
0b01869b | 54 | system call transfers data from the remote process to the local process. |
7985dbf3 | 55 | The data to be transferred is identified by |
1ae6b2c7 | 56 | .I remote_iov |
7985dbf3 MK |
57 | and |
58 | .IR riovcnt : | |
1ae6b2c7 | 59 | .I remote_iov |
7985dbf3 MK |
60 | is a pointer to an array describing address ranges in the process |
61 | .IR pid , | |
62 | and | |
1ae6b2c7 | 63 | .I riovcnt |
0b01869b MK |
64 | specifies the number of elements in |
65 | .IR remote_iov . | |
7985dbf3 | 66 | The data is transferred to the locations specified by |
1ae6b2c7 | 67 | .I local_iov |
7985dbf3 MK |
68 | and |
69 | .IR liovcnt : | |
1ae6b2c7 | 70 | .I local_iov |
7985dbf3 MK |
71 | is a pointer to an array describing address ranges in the calling process, |
72 | and | |
1ae6b2c7 | 73 | .I liovcnt |
0b01869b MK |
74 | specifies the number of elements in |
75 | .IR local_iov . | |
efeece04 | 76 | .PP |
0b0ec758 MF |
77 | The |
78 | .BR process_vm_writev () | |
7985dbf3 | 79 | system call is the converse of |
529b7400 | 80 | .BR process_vm_readv ()\(emit |
0b01869b | 81 | transfers data from the local process to the remote process. |
7985dbf3 MK |
82 | Other than the direction of the transfer, the arguments |
83 | .IR liovcnt , | |
0b01869b | 84 | .IR local_iov , |
04b2e453 | 85 | .IR riovcnt , |
7985dbf3 | 86 | and |
1ae6b2c7 | 87 | .I remote_iov |
7985dbf3 MK |
88 | have the same meaning as for |
89 | .BR process_vm_readv (). | |
efeece04 | 90 | .PP |
7985dbf3 MK |
91 | The |
92 | .I local_iov | |
3960d7a2 | 93 | and |
7985dbf3 MK |
94 | .I remote_iov |
95 | arguments point to an array of | |
529b7400 | 96 | .I iovec |
cb336616 AC |
97 | structures, described in |
98 | .BR iovec (3type). | |
efeece04 | 99 | .PP |
7985dbf3 MK |
100 | Buffers are processed in array order. |
101 | This means that | |
0b0ec758 | 102 | .BR process_vm_readv () |
3960d7a2 | 103 | completely fills |
7985dbf3 | 104 | .I local_iov[0] |
3960d7a2 | 105 | before proceeding to |
7985dbf3 MK |
106 | .IR local_iov[1] , |
107 | and so on. | |
108 | Likewise, | |
109 | .I remote_iov[0] | |
3960d7a2 | 110 | is completely read before proceeding to |
7985dbf3 | 111 | .IR remote_iov[1] , |
529b7400 | 112 | and so on. |
efeece04 | 113 | .PP |
0b0ec758 MF |
114 | Similarly, |
115 | .BR process_vm_writev () | |
3960d7a2 | 116 | writes out the entire contents of |
7985dbf3 | 117 | .I local_iov[0] |
529b7400 | 118 | before proceeding to |
7985dbf3 | 119 | .IR local_iov[1] , |
3960d7a2 | 120 | and it completely fills |
0b01869b | 121 | .I remote_iov[0] |
3960d7a2 | 122 | before proceeding to |
7985dbf3 | 123 | .IR remote_iov[1] . |
efeece04 | 124 | .PP |
3960d7a2 | 125 | The lengths of |
7985dbf3 | 126 | .I remote_iov[i].iov_len |
3960d7a2 | 127 | and |
7985dbf3 | 128 | .I local_iov[i].iov_len |
529b7400 | 129 | do not have to be the same. |
7985dbf3 MK |
130 | Thus, it is possible to split a single local buffer |
131 | into multiple remote buffers, or vice versa. | |
efeece04 | 132 | .PP |
3960d7a2 | 133 | The |
7985dbf3 MK |
134 | .I flags |
135 | argument is currently unused and must be set to 0. | |
efeece04 | 136 | .PP |
7985dbf3 MK |
137 | The values specified in the |
138 | .I liovcnt | |
0b0ec758 | 139 | and |
7985dbf3 MK |
140 | .I riovcnt |
141 | arguments must be less than or equal to | |
1ae6b2c7 | 142 | .B IOV_MAX |
7985dbf3 MK |
143 | (defined in |
144 | .I <limits.h> | |
145 | or accessible via the call | |
146 | .IR sysconf(_SC_IOV_MAX) ). | |
147 | .\" In time, glibc might provide a wrapper that works around this limit, | |
148 | .\" as is done for readv()/writev() | |
efeece04 | 149 | .PP |
7985dbf3 | 150 | The count arguments and |
1ae6b2c7 | 151 | .I local_iov |
7985dbf3 MK |
152 | are checked before doing any transfers. |
153 | If the counts are too big, or | |
0b01869b | 154 | .I local_iov |
7985dbf3 | 155 | is invalid, |
0b01869b MK |
156 | or the addresses refer to regions that are inaccessible to the local process, |
157 | none of the vectors will be processed | |
158 | and an error will be returned immediately. | |
efeece04 | 159 | .PP |
7985dbf3 MK |
160 | Note, however, that these system calls do not check the memory regions |
161 | in the remote process until just before doing the read/write. | |
04b2e453 MK |
162 | Consequently, a partial read/write (see RETURN VALUE) |
163 | may result if one of the | |
0b01869b | 164 | .I remote_iov |
7985dbf3 MK |
165 | elements points to an invalid memory region in the remote process. |
166 | No further reads/writes will be attempted beyond that point. | |
04b2e453 MK |
167 | Keep this in mind when attempting to read data of unknown length |
168 | (such as C strings that are null-terminated) from a remote process, | |
ee8655b5 | 169 | by avoiding spanning memory pages (typically 4\ KiB) in a single remote |
04b2e453 MK |
170 | .I iovec |
171 | element. | |
3960d7a2 | 172 | (Instead, split the remote read into two |
04b2e453 MK |
173 | .I remote_iov |
174 | elements and have them merge back into a single write | |
175 | .I local_iov | |
176 | entry. | |
177 | The first read entry goes up to the page boundary, | |
178 | while the second starts on the next page boundary.) | |
efeece04 | 179 | .PP |
408c8172 MK |
180 | Permission to read from or write to another process |
181 | is governed by a ptrace access mode | |
182 | .B PTRACE_MODE_ATTACH_REALCREDS | |
183 | check; see | |
184 | .BR ptrace (2). | |
47297adb | 185 | .SH RETURN VALUE |
0b0ec758 MF |
186 | On success, |
187 | .BR process_vm_readv () | |
7985dbf3 | 188 | returns the number of bytes read and |
0b0ec758 MF |
189 | .BR process_vm_writev () |
190 | returns the number of bytes written. | |
0b01869b | 191 | This return value may be less than the total number of requested bytes, |
7985dbf3 | 192 | if a partial read/write occurred. |
3960d7a2 | 193 | (Partial transfers apply at the granularity of |
0b01869b MK |
194 | .I iovec |
195 | elements. | |
196 | These system calls won't perform a partial transfer that splits a single | |
197 | .I iovec | |
198 | element.) | |
7985dbf3 | 199 | The caller should check the return value to determine whether |
0b01869b | 200 | a partial read/write occurred. |
efeece04 | 201 | .PP |
7985dbf3 | 202 | On error, \-1 is returned and |
0b0ec758 | 203 | .I errno |
f6a4078b | 204 | is set to indicate the error. |
0b0ec758 MF |
205 | .SH ERRORS |
206 | .TP | |
7071fdf8 MK |
207 | .B EFAULT |
208 | The memory described by | |
209 | .I local_iov | |
210 | is outside the caller's accessible address space. | |
211 | .TP | |
212 | .B EFAULT | |
213 | The memory described by | |
214 | .I remote_iov | |
215 | is outside the accessible address space of the process | |
216 | .IR pid . | |
217 | .TP | |
0b0ec758 | 218 | .B EINVAL |
3960d7a2 | 219 | The sum of the |
529b7400 | 220 | .I iov_len |
3960d7a2 | 221 | values of either |
7985dbf3 | 222 | .I local_iov |
3960d7a2 | 223 | or |
7985dbf3 | 224 | .I remote_iov |
529b7400 MK |
225 | overflows a |
226 | .I ssize_t | |
227 | value. | |
0b0ec758 MF |
228 | .TP |
229 | .B EINVAL | |
529b7400 | 230 | .I flags |
7985dbf3 MK |
231 | is not 0. |
232 | .TP | |
233 | .B EINVAL | |
234 | .I liovcnt | |
235 | or | |
236 | .I riovcnt | |
237 | is too large. | |
0b0ec758 | 238 | .TP |
0b0ec758 | 239 | .B ENOMEM |
0b01869b MK |
240 | Could not allocate memory for internal copies of the |
241 | .I iovec | |
242 | structures. | |
0b0ec758 MF |
243 | .TP |
244 | .B EPERM | |
7985dbf3 | 245 | The caller does not have permission to access the address space of the process |
529b7400 | 246 | .IR pid . |
0b0ec758 MF |
247 | .TP |
248 | .B ESRCH | |
7985dbf3 | 249 | No process with ID |
529b7400 | 250 | .I pid |
7985dbf3 | 251 | exists. |
0b0ec758 | 252 | .SH VERSIONS |
7985dbf3 MK |
253 | These system calls were added in Linux 3.2. |
254 | Support is provided in glibc since version 2.15. | |
3113c7f3 | 255 | .SH STANDARDS |
7985dbf3 MK |
256 | These system calls are nonstandard Linux extensions. |
257 | .SH NOTES | |
258 | The data transfers performed by | |
259 | .BR process_vm_readv () | |
260 | and | |
261 | .BR process_vm_writev () | |
262 | are not guaranteed to be atomic in any way. | |
efeece04 | 263 | .PP |
7985dbf3 MK |
264 | These system calls were designed to permit fast message passing |
265 | by allowing messages to be exchanged with a single copy operation | |
266 | (rather than the double copy that would be required | |
267 | when using, for example, shared memory or pipes). | |
268 | .\" Original user is MPI, http://www.mcs.anl.gov/research/projects/mpi/ | |
269 | .\" See also some benchmarks at http://lwn.net/Articles/405284/ | |
270 | .\" and http://marc.info/?l=linux-mm&m=130105930902915&w=2 | |
a14af333 | 271 | .SH EXAMPLES |
529b7400 MK |
272 | The following code sample demonstrates the use of |
273 | .BR process_vm_readv (). | |
3960d7a2 | 274 | It reads 20 bytes at the address 0x10000 from the process with PID 10 |
529b7400 MK |
275 | and writes the first 10 bytes into |
276 | .I buf1 | |
277 | and the second 10 bytes into | |
278 | .IR buf2 . | |
51f5698d | 279 | .PP |
33857069 | 280 | .\" SRC BEGIN (process_vm_readv.c) |
408731d4 | 281 | .EX |
2f5c165c | 282 | #define _GNU_SOURCE |
f2bdc79c AC |
283 | #include <stdlib.h> |
284 | #include <sys/types.h> | |
0b0ec758 MF |
285 | #include <sys/uio.h> |
286 | ||
9762bc8a MK |
287 | int |
288 | main(void) | |
0b0ec758 | 289 | { |
0b94bd78 AC |
290 | char buf1[10]; |
291 | char buf2[10]; | |
292 | pid_t pid = 10; /* PID of remote process */ | |
293 | ssize_t nread; | |
294 | struct iovec local[2]; | |
295 | struct iovec remote[1]; | |
0b0ec758 MF |
296 | |
297 | local[0].iov_base = buf1; | |
298 | local[0].iov_len = 10; | |
299 | local[1].iov_base = buf2; | |
300 | local[1].iov_len = 10; | |
9762bc8a | 301 | remote[0].iov_base = (void *) 0x10000; |
0e42c515 | 302 | remote[0].iov_len = 20; |
0b0ec758 MF |
303 | |
304 | nread = process_vm_readv(pid, local, 2, remote, 1, 0); | |
305 | if (nread != 20) | |
17bb9b18 AC |
306 | exit(EXIT_FAILURE); |
307 | ||
308 | exit(EXIT_SUCCESS); | |
0b0ec758 | 309 | } |
408731d4 | 310 | .EE |
33857069 | 311 | .\" SRC END |
47297adb | 312 | .SH SEE ALSO |
0b0ec758 MF |
313 | .BR readv (2), |
314 | .BR writev (2) |