blob: 17b33f677f0d742b85732566f4557b43a8ce00d6 [file] [log] [blame]
sewardj55f9d1a2005-04-25 11:11:44 +00001
2/*--------------------------------------------------------------------*/
njn43b9a8a2005-05-10 04:37:01 +00003/*--- The address space manager. pub_core_aspacemgr.h ---*/
sewardj55f9d1a2005-04-25 11:11:44 +00004/*--------------------------------------------------------------------*/
5
6/*
7 This file is part of Valgrind, a dynamic binary instrumentation
8 framework.
9
sewardj03f8d3f2012-08-05 15:46:46 +000010 Copyright (C) 2000-2012 Julian Seward
sewardj55f9d1a2005-04-25 11:11:44 +000011 jseward@acm.org
12
13 This program is free software; you can redistribute it and/or
14 modify it under the terms of the GNU General Public License as
15 published by the Free Software Foundation; either version 2 of the
16 License, or (at your option) any later version.
17
18 This program is distributed in the hope that it will be useful, but
19 WITHOUT ANY WARRANTY; without even the implied warranty of
20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21 General Public License for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with this program; if not, write to the Free Software
25 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
26 02111-1307, USA.
27
28 The GNU General Public License is contained in the file COPYING.
29*/
30
31#ifndef __PUB_CORE_ASPACEMGR_H
32#define __PUB_CORE_ASPACEMGR_H
33
34//--------------------------------------------------------------------
35// PURPOSE: This module deals with management of the entire process
36// address space. Almost everything depends upon it, including dynamic
37// memory management. Hence this module is almost completely
38// standalone; the only module it uses is m_debuglog. DO NOT CHANGE
39// THIS.
40//--------------------------------------------------------------------
41
njn4802b382005-06-11 04:58:29 +000042#include "pub_tool_aspacemgr.h"
sewardj55f9d1a2005-04-25 11:11:44 +000043
sewardj45f4e7c2005-09-27 19:20:21 +000044//--------------------------------------------------------------
45// Definition of address-space segments
46
47/* types SegKind, ShrinkMode and NSegment are described in
48 the tool-visible header file, not here. */
49
50
51//--------------------------------------------------------------
52// Initialisation
53
54/* Initialise the address space manager, setting up the initial
55 segment list, and reading /proc/self/maps into it. This must
56 be called before any other function.
57
58 Takes a pointer to the SP at the time V gained control. This is
59 taken to be the highest usable address (more or less). Based on
60 that (and general consultation of tea leaves, etc) return a
61 suggested end address for the client's stack. */
62extern Addr VG_(am_startup) ( Addr sp_at_startup );
63
64
65//--------------------------------------------------------------
66// Querying current status
67
68/* Finds the segment containing 'a'. Only returns file/anon/resvn
sewardjfa2a2462006-10-17 01:30:07 +000069 segments. This returns a 'NSegment const *' - a pointer to
70 readonly data. */
sewardj45f4e7c2005-09-27 19:20:21 +000071// Is in tool-visible header file.
sewardjfa2a2462006-10-17 01:30:07 +000072// extern NSegment const * VG_(am_find_nsegment) ( Addr a );
sewardj45f4e7c2005-09-27 19:20:21 +000073
74/* Find the next segment along from 'here', if it is a file/anon/resvn
75 segment. */
florian3e798632012-11-24 19:41:54 +000076extern NSegment const* VG_(am_next_nsegment) ( const NSegment* here,
77 Bool fwds );
sewardj45f4e7c2005-09-27 19:20:21 +000078
79/* Is the area [start .. start+len-1] validly accessible by the
80 client with at least the permissions 'prot' ? To find out
81 simply if said area merely belongs to the client, pass
82 VKI_PROT_NONE as 'prot'. Will return False if any part of the
83 area does not belong to the client or does not have at least
84 the stated permissions. */
85// Is in tool-visible header file.
86// extern Bool VG_(am_is_valid_for_client)
87// ( Addr start, SizeT len, UInt prot );
88
89/* Variant of VG_(am_is_valid_for_client) which allows free areas to
90 be consider part of the client's addressable space. It also
91 considers reservations to be allowable, since from the client's
92 point of view they don't exist. */
93extern Bool VG_(am_is_valid_for_client_or_free_or_resvn)
94 ( Addr start, SizeT len, UInt prot );
95
96/* Trivial fn: return the total amount of space in anonymous mappings,
97 both for V and the client. Is used for printing stats in
98 out-of-memory messages. */
99extern ULong VG_(am_get_anonsize_total)( void );
100
101/* Show the segment array on the debug log, at given loglevel. */
floriandbb35842012-10-27 18:39:11 +0000102extern void VG_(am_show_nsegments) ( Int logLevel, const HChar* who );
sewardj45f4e7c2005-09-27 19:20:21 +0000103
104/* Get the filename corresponding to this segment, if known and if it
105 has one. The returned name's storage cannot be assumed to be
106 persistent, so the caller should immediately copy the name
sewardj7cf4e6b2008-05-01 20:24:26 +0000107 elsewhere. This may return NULL if the file name is not known or
108 for arbitrary other implementation-dependent reasons, so callers
109 need to be able to handle a NULL return value. */
tombcaf0472005-11-16 00:11:14 +0000110// Is in tool-visible header file.
111// extern HChar* VG_(am_get_filename)( NSegment* );
sewardj45f4e7c2005-09-27 19:20:21 +0000112
113/* VG_(am_get_segment_starts) is also part of this section, but its
114 prototype is tool-visible, hence not in this header file. */
115
116/* Sanity check: check that Valgrind and the kernel agree on the
117 address space layout. Prints offending segments and call point if
118 a discrepancy is detected, but does not abort the system. Returned
119 Bool is False if a discrepancy was found. */
120
121extern Bool VG_(am_do_sync_check) ( const HChar* fn,
122 const HChar* file, Int line );
123
sewardj45f4e7c2005-09-27 19:20:21 +0000124//--------------------------------------------------------------
125// Functions pertaining to the central query-notify mechanism
126// used to handle mmap/munmap/mprotect resulting from client
127// syscalls.
128
129/* Describes a request for VG_(am_get_advisory). */
130typedef
131 struct {
132 enum { MFixed, MHint, MAny } rkind;
133 Addr start;
134 Addr len;
135 }
136 MapRequest;
137
138/* Query aspacem to ask where a mapping should go. On success, the
139 advised placement is returned, and *ok is set to True. On failure,
140 zero is returned and *ok is set to False. Note that *ok must be
141 consulted by the caller to establish success or failure; that
142 cannot be established reliably from the returned value. If *ok is
143 set to False, it means aspacem has vetoed the mapping, and so the
144 caller should not proceed with it. */
145extern Addr VG_(am_get_advisory)
146 ( MapRequest* req, Bool forClient, /*OUT*/Bool* ok );
147
148/* Convenience wrapper for VG_(am_get_advisory) for client floating or
149 fixed requests. If start is zero, a floating request is issued; if
150 nonzero, a fixed request at that address is issued. Same comments
151 about return values apply. */
152extern Addr VG_(am_get_advisory_client_simple)
153 ( Addr start, SizeT len, /*OUT*/Bool* ok );
154
philippe15e301e2011-12-22 13:25:58 +0000155/* Returns True if [start, start + len - 1] is covered by a single
156 free segment, otherwise returns False.
157 This allows to check the following case:
158 VG_(am_get_advisory_client_simple) (first arg == 0, meaning
159 this-or-nothing) is too lenient, and may allow us to trash
160 the next segment along. So make very sure that the proposed
161 new area really is free. This is perhaps overly
162 conservative, but it fixes #129866. */
163extern Bool VG_(am_covered_by_single_free_segment)
164 ( Addr start, SizeT len);
165
sewardj45f4e7c2005-09-27 19:20:21 +0000166/* Notifies aspacem that the client completed an mmap successfully.
167 The segment array is updated accordingly. If the returned Bool is
168 True, the caller should immediately discard translations from the
169 specified address range. */
170extern Bool VG_(am_notify_client_mmap)
sewardj274461d2005-10-02 17:01:41 +0000171 ( Addr a, SizeT len, UInt prot, UInt flags, Int fd, Off64T offset );
sewardj45f4e7c2005-09-27 19:20:21 +0000172
tom1340c352005-10-04 15:59:54 +0000173/* Notifies aspacem that the client completed a shmat successfully.
174 The segment array is updated accordingly. If the returned Bool is
175 True, the caller should immediately discard translations from the
176 specified address range. */
177extern Bool VG_(am_notify_client_shmat)( Addr a, SizeT len, UInt prot );
178
sewardj45f4e7c2005-09-27 19:20:21 +0000179/* Notifies aspacem that an mprotect was completed successfully. The
180 segment array is updated accordingly. Note, as with
181 VG_(am_notify_munmap), it is not the job of this function to reject
182 stupid mprotects, for example the client doing mprotect of
183 non-client areas. Such requests should be intercepted earlier, by
184 the syscall wrapper for mprotect. This function merely records
185 whatever it is told. If the returned Bool is True, the caller
186 should immediately discard translations from the specified address
187 range. */
188extern Bool VG_(am_notify_mprotect)( Addr start, SizeT len, UInt prot );
189
190/* Notifies aspacem that an munmap completed successfully. The
191 segment array is updated accordingly. As with
192 VG_(am_notify_munmap), we merely record the given info, and don't
193 check it for sensibleness. If the returned Bool is True, the
194 caller should immediately discard translations from the specified
195 address range. */
196extern Bool VG_(am_notify_munmap)( Addr start, SizeT len );
197
sewardj45f4e7c2005-09-27 19:20:21 +0000198/* Hand a raw mmap to the kernel, without aspacem updating the segment
199 array. THIS FUNCTION IS DANGEROUS -- it will cause aspacem's view
200 of the address space to diverge from that of the kernel. DO NOT
201 USE IT UNLESS YOU UNDERSTAND the request-notify model used by
202 aspacem. In short, DO NOT USE THIS FUNCTION. */
203extern SysRes VG_(am_do_mmap_NO_NOTIFY)
njn9506f0d2009-05-20 03:20:05 +0000204 ( Addr start, SizeT length, UInt prot, UInt flags, Int fd, Off64T offset);
sewardj45f4e7c2005-09-27 19:20:21 +0000205
206
207//--------------------------------------------------------------
208// Dealing with mappings which do not arise directly from the
209// simulation of the client. These are typically used for
210// loading the client and building its stack/data segment, before
211// execution begins. Also for V's own administrative use.
212
213/* --- --- --- map, unmap, protect --- --- --- */
214
215/* Map a file at a fixed address for the client, and update the
216 segment array accordingly. */
217extern SysRes VG_(am_mmap_file_fixed_client)
sewardj274461d2005-10-02 17:01:41 +0000218 ( Addr start, SizeT length, UInt prot, Int fd, Off64T offset );
njnf76d27a2009-05-28 01:53:07 +0000219extern SysRes VG_(am_mmap_named_file_fixed_client)
220 ( Addr start, SizeT length, UInt prot, Int fd, Off64T offset, const HChar *name );
sewardj45f4e7c2005-09-27 19:20:21 +0000221
222/* Map anonymously at a fixed address for the client, and update
223 the segment array accordingly. */
224extern SysRes VG_(am_mmap_anon_fixed_client)
225 ( Addr start, SizeT length, UInt prot );
226
sewardjfa2a2462006-10-17 01:30:07 +0000227
sewardj45f4e7c2005-09-27 19:20:21 +0000228/* Map anonymously at an unconstrained address for the client, and
229 update the segment array accordingly. */
230extern SysRes VG_(am_mmap_anon_float_client) ( SizeT length, Int prot );
231
sewardjfa2a2462006-10-17 01:30:07 +0000232/* Similarly, acquire new address space for the client but with
233 considerable restrictions on what can be done with it: (1) the
234 actual protections may exceed those stated in 'prot', (2) the
235 area's protections cannot be later changed using any form of
236 mprotect, and (3) the area cannot be freed using any form of
237 munmap. On Linux this behaves the same as
238 VG_(am_mmap_anon_float_client). On AIX5 this *may* allocate memory
239 by using sbrk, so as to make use of large pages on AIX. */
240extern SysRes VG_(am_sbrk_anon_float_client) ( SizeT length, Int prot );
241
242
sewardj45f4e7c2005-09-27 19:20:21 +0000243/* Map anonymously at an unconstrained address for V, and update the
244 segment array accordingly. This is fundamentally how V allocates
245 itself more address space when needed. */
246extern SysRes VG_(am_mmap_anon_float_valgrind)( SizeT cszB );
247
sewardjfa2a2462006-10-17 01:30:07 +0000248/* Same comments apply as per VG_(am_sbrk_anon_float_client). On
249 Linux this behaves the same as VG_(am_mmap_anon_float_valgrind). */
250extern SysRes VG_(am_sbrk_anon_float_valgrind)( SizeT cszB );
251
252
sewardj3b290482011-05-06 21:02:55 +0000253/* Map privately a file at an unconstrained address for V, and update the
sewardj45f4e7c2005-09-27 19:20:21 +0000254 segment array accordingly. This is used by V for transiently
255 mapping in object files to read their debug info. */
256extern SysRes VG_(am_mmap_file_float_valgrind)
sewardj274461d2005-10-02 17:01:41 +0000257 ( SizeT length, UInt prot, Int fd, Off64T offset );
sewardj45f4e7c2005-09-27 19:20:21 +0000258
sewardj3b290482011-05-06 21:02:55 +0000259/* Map shared a file at an unconstrained address for V, and update the
260 segment array accordingly. This is used by V for communicating
261 with vgdb. */
262extern SysRes VG_(am_shared_mmap_file_float_valgrind)
263 ( SizeT length, UInt prot, Int fd, Off64T offset );
264
sewardj45f4e7c2005-09-27 19:20:21 +0000265/* Unmap the given address range and update the segment array
266 accordingly. This fails if the range isn't valid for the client.
267 If *need_discard is True after a successful return, the caller
268 should immediately discard translations from the specified address
269 range. */
270extern SysRes VG_(am_munmap_client)( /*OUT*/Bool* need_discard,
271 Addr start, SizeT length );
272
sewardj45f4e7c2005-09-27 19:20:21 +0000273/* Let (start,len) denote an area within a single Valgrind-owned
274 segment (anon or file). Change the ownership of [start, start+len)
275 to the client instead. Fails if (start,len) does not denote a
276 suitable segment. */
277extern Bool VG_(am_change_ownership_v_to_c)( Addr start, SizeT len );
278
sewardjfa2a2462006-10-17 01:30:07 +0000279/* 'seg' must be NULL or have been obtained from
280 VG_(am_find_nsegment), and still valid. If non-NULL, and if it
281 denotes a SkAnonC (anonymous client mapping) area, set the .isCH
282 (is-client-heap) flag for that area. Otherwise do nothing.
283 (Bizarre interface so that the same code works for both Linux and
284 AIX and does not impose inefficiencies on the Linux version.) */
florian3e798632012-11-24 19:41:54 +0000285extern void VG_(am_set_segment_isCH_if_SkAnonC)( const NSegment* seg );
sewardjfa2a2462006-10-17 01:30:07 +0000286
287/* Same idea as VG_(am_set_segment_isCH_if_SkAnonC), except set the
288 segment's hasT bit (has-cached-code) if this is SkFileC or SkAnonC
289 segment. */
florian3e798632012-11-24 19:41:54 +0000290extern void VG_(am_set_segment_hasT_if_SkFileC_or_SkAnonC)( const NSegment* );
sewardjfa2a2462006-10-17 01:30:07 +0000291
sewardj45f4e7c2005-09-27 19:20:21 +0000292/* --- --- --- reservations --- --- --- */
293
294/* Create a reservation from START .. START+LENGTH-1, with the given
295 ShrinkMode. When checking whether the reservation can be created,
296 also ensure that at least abs(EXTRA) extra free bytes will remain
297 above (> 0) or below (< 0) the reservation.
298
299 The reservation will only be created if it, plus the extra-zone,
300 falls entirely within a single free segment. The returned Bool
301 indicates whether the creation succeeded. */
302extern Bool VG_(am_create_reservation)
303 ( Addr start, SizeT length, ShrinkMode smode, SSizeT extra );
304
305/* Let SEG be an anonymous client mapping. This fn extends the
306 mapping by DELTA bytes, taking the space from a reservation section
307 which must be adjacent. If DELTA is positive, the segment is
308 extended forwards in the address space, and the reservation must be
309 the next one along. If DELTA is negative, the segment is extended
310 backwards in the address space and the reservation must be the
sewardj6684d2a2005-09-28 01:46:31 +0000311 previous one. DELTA must be page aligned. abs(DELTA) must not
312 exceed the size of the reservation segment minus one page, that is,
313 the reservation segment after the operation must be at least one
314 page long. */
sewardj45f4e7c2005-09-27 19:20:21 +0000315extern Bool VG_(am_extend_into_adjacent_reservation_client)
florian3e798632012-11-24 19:41:54 +0000316 ( const NSegment* seg, SSizeT delta );
sewardj45f4e7c2005-09-27 19:20:21 +0000317
318/* --- --- --- resizing/move a mapping --- --- --- */
319
320/* Let SEG be a client mapping (anonymous or file). This fn extends
321 the mapping forwards only by DELTA bytes, and trashes whatever was
322 in the new area. Fails if SEG is not a single client mapping or if
323 the new area is not accessible to the client. Fails if DELTA is
324 not page aligned. *seg is invalid after a successful return. If
325 *need_discard is True after a successful return, the caller should
326 immediately discard translations from the new area. */
327extern Bool VG_(am_extend_map_client)( /*OUT*/Bool* need_discard,
florian3e798632012-11-24 19:41:54 +0000328 const NSegment* seg, SizeT delta );
sewardj45f4e7c2005-09-27 19:20:21 +0000329
330/* Remap the old address range to the new address range. Fails if any
331 parameter is not page aligned, if the either size is zero, if any
332 wraparound is implied, if the old address range does not fall
333 entirely within a single segment, if the new address range overlaps
334 with the old one, or if the old address range is not a valid client
335 mapping. If *need_discard is True after a successful return, the
336 caller should immediately discard translations from both specified
337 address ranges. */
338extern Bool VG_(am_relocate_nooverlap_client)( /*OUT*/Bool* need_discard,
339 Addr old_addr, SizeT old_len,
340 Addr new_addr, SizeT new_len );
341
342//--------------------------------------------------------------
343// Valgrind (non-client) thread stacks. V itself runs on such
344// stacks. The address space manager provides and suitably
345// protects such stacks.
346
sewardj5db15402012-06-07 09:13:21 +0000347#if defined(VGP_ppc32_linux) || defined(VGP_ppc64_linux) \
348 || defined(VGP_mips32_linux)
sewardje66f2e02006-12-30 17:45:08 +0000349# define VG_STACK_GUARD_SZB 65536 // 1 or 16 pages
sewardj9e0a6b82010-07-21 09:49:27 +0000350# define VG_STACK_ACTIVE_SZB (4096 * 256) // 1Mb
sewardje66f2e02006-12-30 17:45:08 +0000351#else
352# define VG_STACK_GUARD_SZB 8192 // 2 pages
sewardj9e0a6b82010-07-21 09:49:27 +0000353# define VG_STACK_ACTIVE_SZB (4096 * 256) // 1Mb
sewardje66f2e02006-12-30 17:45:08 +0000354#endif
sewardj45f4e7c2005-09-27 19:20:21 +0000355
356typedef
357 struct {
358 HChar bytes[VG_STACK_GUARD_SZB
359 + VG_STACK_ACTIVE_SZB
360 + VG_STACK_GUARD_SZB];
361 }
362 VgStack;
363
364
365/* Allocate and initialise a VgStack (anonymous client space).
366 Protect the stack active area and the guard areas appropriately.
367 Returns NULL on failure, else the address of the bottom of the
368 stack. On success, also sets *initial_sp to what the stack pointer
369 should be set to. */
370
371extern VgStack* VG_(am_alloc_VgStack)( /*OUT*/Addr* initial_sp );
372
sewardj46dbd3f2010-09-08 08:30:31 +0000373/* Figure out how many bytes of the stack's active area have not been
374 used. Used for estimating if we are close to overflowing it. If
375 the free area is larger than 'limit', just return 'limit'. */
376extern SizeT VG_(am_get_VgStack_unused_szB)( VgStack* stack, SizeT limit );
sewardj45f4e7c2005-09-27 19:20:21 +0000377
njnf76d27a2009-05-28 01:53:07 +0000378// DDD: this is ugly
379#if defined(VGO_darwin)
380typedef
381 struct {
382 Bool is_added; // Added or removed seg?
383 Addr start;
384 SizeT end;
385 UInt prot; // Not used for removed segs.
386 Off64T offset; // Not used for removed segs.
387 }
388 ChangedSeg;
389
njnfd1b4612009-06-24 08:32:42 +0000390extern Bool VG_(get_changed_segments)(
njnf76d27a2009-05-28 01:53:07 +0000391 const HChar* when, const HChar* where, /*OUT*/ChangedSeg* css,
392 Int css_size, /*OUT*/Int* css_used);
393#endif
njne3f06352005-06-01 03:48:33 +0000394
sewardj55f9d1a2005-04-25 11:11:44 +0000395#endif // __PUB_CORE_ASPACEMGR_H
396
397/*--------------------------------------------------------------------*/
njnaf839f52005-06-23 03:27:57 +0000398/*--- end ---*/
sewardj55f9d1a2005-04-25 11:11:44 +0000399/*--------------------------------------------------------------------*/