summaryrefslogtreecommitdiff
blob: d2b065a3b6e0d70a6d67041eee2fc2a6747ea91d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
From c443b67561891ae68d688daf5f8ce37820cdba2b Mon Sep 17 00:00:00 2001
From: Jason Evans <jasone@canonware.com>
Date: Sat, 29 Oct 2016 22:41:04 -0700
Subject: [PATCH] Use syscall(2) rather than {open,read,close}(2) during boot.

Some applications wrap various system calls, and if they call the
allocator in their wrappers, unexpected reentry can result.  This is not
a general solution (many other syscalls are spread throughout the code),
but this resolves a bootstrapping issue that is apparently common.

This resolves #443.
---
 src/pages.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/src/pages.c b/src/pages.c
index 05b0d69..84e2216 100644
--- a/src/pages.c
+++ b/src/pages.c
@@ -207,6 +207,11 @@ os_overcommits_sysctl(void)
 #endif
 
 #ifdef JEMALLOC_PROC_SYS_VM_OVERCOMMIT_MEMORY
+/*
+ * Use syscall(2) rather than {open,read,close}(2) when possible to avoid
+ * reentry during bootstrapping if another library has interposed system call
+ * wrappers.
+ */
 static bool
 os_overcommits_proc(void)
 {
@@ -214,12 +219,26 @@ os_overcommits_proc(void)
 	char buf[1];
 	ssize_t nread;
 
+#ifdef SYS_open
+	fd = (int)syscall(SYS_open, "/proc/sys/vm/overcommit_memory", O_RDONLY);
+#else
 	fd = open("/proc/sys/vm/overcommit_memory", O_RDONLY);
+#endif
 	if (fd == -1)
 		return (false); /* Error. */
 
+#ifdef SYS_read
+	nread = (ssize_t)syscall(SYS_read, fd, &buf, sizeof(buf));
+#else
 	nread = read(fd, &buf, sizeof(buf));
+#endif
+
+#ifdef SYS_close
+	syscall(SYS_close, fd);
+#else
 	close(fd);
+#endif
+
 	if (nread < 1)
 		return (false); /* Error. */
 	/*