Skip to content

Commit 32b4ef6

Browse files
committed
[msan] Support prctl PR_GET_NAME call
Per the man page, PR_GET_NAME stores a null terminated string into the input `char name[16]`. This also adds prctl support in ASAN to detect freed memory being passed to `prctl(PR_GET_NAME, ...)`:
1 parent da286c8 commit 32b4ef6

File tree

2 files changed

+37
-1
lines changed

2 files changed

+37
-1
lines changed

compiler-rt/lib/sanitizer_common/sanitizer_common_interceptors.inc

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1251,6 +1251,7 @@ INTERCEPTOR(int, prctl, int option, unsigned long arg2, unsigned long arg3,
12511251
void *ctx;
12521252
COMMON_INTERCEPTOR_ENTER(ctx, prctl, option, arg2, arg3, arg4, arg5);
12531253
static const int PR_SET_NAME = 15;
1254+
static const int PR_GET_NAME = 16;
12541255
static const int PR_SET_VMA = 0x53564d41;
12551256
static const int PR_SCHED_CORE = 62;
12561257
static const int PR_SCHED_CORE_GET = 0;
@@ -1264,7 +1265,18 @@ INTERCEPTOR(int, prctl, int option, unsigned long arg2, unsigned long arg3,
12641265
internal_strncpy(buff, (char *)arg2, 15);
12651266
buff[15] = 0;
12661267
COMMON_INTERCEPTOR_SET_THREAD_NAME(ctx, buff);
1267-
} else if (res != -1 && option == PR_SCHED_CORE && arg2 == PR_SCHED_CORE_GET) {
1268+
} else if (res != 1 && option == PR_GET_NAME) {
1269+
unsigned long null_index = 0;
1270+
char *name = (char *)arg2;
1271+
while (null_index < 16 && name[null_index]) {
1272+
++null_index;
1273+
}
1274+
if (null_index > 15) {
1275+
null_index = 15;
1276+
}
1277+
COMMON_INTERCEPTOR_WRITE_RANGE(ctx, (u64 *)arg2, null_index + 1);
1278+
} else if (res != -1 && option == PR_SCHED_CORE &&
1279+
arg2 == PR_SCHED_CORE_GET) {
12681280
COMMON_INTERCEPTOR_WRITE_RANGE(ctx, (u64*)(arg5), sizeof(u64));
12691281
}
12701282
return res;

compiler-rt/test/msan/prctl.cpp

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
// RUN: %clangxx_msan -O0 %s -o %t && not %run %t 2>&1 | FileCheck %s
2+
// REQUIRES: linux
3+
4+
#include <linux/prctl.h>
5+
#include <sys/prctl.h>
6+
7+
int main(void) {
8+
prctl(PR_SET_NAME, "tname");
9+
char name[16];
10+
prctl(PR_GET_NAME, name);
11+
12+
if (name[0] == 'A') {
13+
return 0;
14+
}
15+
if (name[5] != '\0') {
16+
return 0;
17+
}
18+
if (name[6] != '\0') {
19+
return 0;
20+
}
21+
// CHECK: SUMMARY: MemorySanitizer: use-of-uninitialized-value {{.*prctl.cpp}}:[[@LINE-3]]
22+
23+
return 0;
24+
}

0 commit comments

Comments
 (0)