Skip to content

Commit 01ee356

Browse files
committed
name anonymous mmap address ranges for debugging on Linux (based on PR #1032 by @zhuker)
1 parent fdde679 commit 01ee356

File tree

1 file changed

+18
-8
lines changed

1 file changed

+18
-8
lines changed

src/prim/unix/prim.c

Lines changed: 18 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -205,14 +205,24 @@ static int unix_madvise(void* addr, size_t size, int advice) {
205205
return (res==0 ? 0 : errno);
206206
}
207207

208-
static void* unix_mmap_prim(void* addr, size_t size, size_t try_alignment, int protect_flags, int flags, int fd) {
208+
static void* unix_mmap_prim(void* addr, size_t size, int protect_flags, int flags, int fd) {
209+
void* p = mmap(addr, size, protect_flags, flags, fd, 0 /* offset */);
210+
#if (defined(__linux__) || defined(__ANDROID__))
211+
if (p!=MAP_FAILED && p!=NULL) {
212+
prctl(PR_SET_VMA, PR_SET_VMA_ANON_NAME, p, size, "mimalloc");
213+
}
214+
#endif
215+
return p;
216+
}
217+
218+
static void* unix_mmap_prim_aligned(void* addr, size_t size, size_t try_alignment, int protect_flags, int flags, int fd) {
209219
MI_UNUSED(try_alignment);
210220
void* p = NULL;
211221
#if defined(MAP_ALIGNED) // BSD
212222
if (addr == NULL && try_alignment > 1 && (try_alignment % _mi_os_page_size()) == 0) {
213223
size_t n = mi_bsr(try_alignment);
214224
if (((size_t)1 << n) == try_alignment && n >= 12 && n <= 30) { // alignment is a power of 2 and 4096 <= alignment <= 1GiB
215-
p = mmap(addr, size, protect_flags, flags | MAP_ALIGNED(n), fd, 0);
225+
p = unix_mmap_prim(addr, size, protect_flags, flags | MAP_ALIGNED(n), fd);
216226
if (p==MAP_FAILED || !_mi_is_aligned(p,try_alignment)) {
217227
int err = errno;
218228
_mi_trace_message("unable to directly request aligned OS memory (error: %d (0x%x), size: 0x%zx bytes, alignment: 0x%zx, hint address: %p)\n", err, err, size, try_alignment, addr);
@@ -223,7 +233,7 @@ static void* unix_mmap_prim(void* addr, size_t size, size_t try_alignment, int p
223233
}
224234
#elif defined(MAP_ALIGN) // Solaris
225235
if (addr == NULL && try_alignment > 1 && (try_alignment % _mi_os_page_size()) == 0) {
226-
p = mmap((void*)try_alignment, size, protect_flags, flags | MAP_ALIGN, fd, 0); // addr parameter is the required alignment
236+
p = unix_mmap_prim((void*)try_alignment, size, protect_flags, flags | MAP_ALIGN, fd); // addr parameter is the required alignment
227237
if (p!=MAP_FAILED) return p;
228238
// fall back to regular mmap
229239
}
@@ -233,7 +243,7 @@ static void* unix_mmap_prim(void* addr, size_t size, size_t try_alignment, int p
233243
if (addr == NULL) {
234244
void* hint = _mi_os_get_aligned_hint(try_alignment, size);
235245
if (hint != NULL) {
236-
p = mmap(hint, size, protect_flags, flags, fd, 0);
246+
p = unix_mmap_prim(hint, size, protect_flags, flags, fd);
237247
if (p==MAP_FAILED || !_mi_is_aligned(p,try_alignment)) {
238248
#if MI_TRACK_ENABLED // asan sometimes does not instrument errno correctly?
239249
int err = 0;
@@ -248,7 +258,7 @@ static void* unix_mmap_prim(void* addr, size_t size, size_t try_alignment, int p
248258
}
249259
#endif
250260
// regular mmap
251-
p = mmap(addr, size, protect_flags, flags, fd, 0);
261+
p = unix_mmap_prim(addr, size, protect_flags, flags, fd);
252262
if (p!=MAP_FAILED) return p;
253263
// failed to allocate
254264
return NULL;
@@ -319,15 +329,15 @@ static void* unix_mmap(void* addr, size_t size, size_t try_alignment, int protec
319329
if (large_only || lflags != flags) {
320330
// try large OS page allocation
321331
*is_large = true;
322-
p = unix_mmap_prim(addr, size, try_alignment, protect_flags, lflags, lfd);
332+
p = unix_mmap_prim_aligned(addr, size, try_alignment, protect_flags, lflags, lfd);
323333
#ifdef MAP_HUGE_1GB
324334
if (p == NULL && (lflags & MAP_HUGE_1GB) == MAP_HUGE_1GB) {
325335
mi_huge_pages_available = false; // don't try huge 1GiB pages again
326336
if (large_only) {
327337
_mi_warning_message("unable to allocate huge (1GiB) page, trying large (2MiB) pages instead (errno: %i)\n", errno);
328338
}
329339
lflags = ((lflags & ~MAP_HUGE_1GB) | MAP_HUGE_2MB);
330-
p = unix_mmap_prim(addr, size, try_alignment, protect_flags, lflags, lfd);
340+
p = unix_mmap_prim_aligned(addr, size, try_alignment, protect_flags, lflags, lfd);
331341
}
332342
#endif
333343
if (large_only) return p;
@@ -340,7 +350,7 @@ static void* unix_mmap(void* addr, size_t size, size_t try_alignment, int protec
340350
// regular allocation
341351
if (p == NULL) {
342352
*is_large = false;
343-
p = unix_mmap_prim(addr, size, try_alignment, protect_flags, flags, fd);
353+
p = unix_mmap_prim_aligned(addr, size, try_alignment, protect_flags, flags, fd);
344354
if (p != NULL) {
345355
#if defined(MADV_HUGEPAGE)
346356
// Many Linux systems don't allow MAP_HUGETLB but they support instead

0 commit comments

Comments
 (0)