Skip to content

Commit 51a840e

Browse files
authored
[sanitizer_common][tsan][Darwin] Improve message for unsupported vm config on Apple platforms (#158665)
An existing log message is triggered in InitializePlatformEarly if the address space max is not as sufficient for TSAN. Some Apple platforms expand the address space limit, but reserve much of the space TSAN needs. Therefore, we now check that the kernel has not mapped over the address space that we intend to use. IsAddressInMappedRegion is added to sanitizer_common. This introduces a new dependency on mach_vm_region_recurse during TSAN startup, so this intentionally fails softly (to avoid breaking current users who may be in a sandbox that doesn't allow this). rdar://135265279
1 parent acc3a62 commit 51a840e

File tree

3 files changed

+38
-3
lines changed

3 files changed

+38
-3
lines changed

compiler-rt/lib/sanitizer_common/sanitizer_mac.cpp

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1360,6 +1360,29 @@ uptr FindAvailableMemoryRange(uptr size, uptr alignment, uptr left_padding,
13601360
return 0;
13611361
}
13621362

1363+
// Returns true if the address is definitely mapped, and false if it is not
1364+
// mapped or could not be determined.
1365+
bool IsAddressInMappedRegion(uptr addr) {
1366+
mach_vm_size_t vmsize = 0;
1367+
natural_t depth = 0;
1368+
vm_region_submap_short_info_data_64_t vminfo;
1369+
mach_msg_type_number_t count = VM_REGION_SUBMAP_SHORT_INFO_COUNT_64;
1370+
mach_vm_address_t address = addr;
1371+
1372+
kern_return_t kr =
1373+
mach_vm_region_recurse(mach_task_self(), &address, &vmsize, &depth,
1374+
(vm_region_info_t)&vminfo, &count);
1375+
1376+
if (kr == KERN_DENIED) {
1377+
Report(
1378+
"WARN: mach_vm_region_recurse returned KERN_DENIED when checking "
1379+
"whether an address is mapped.\n");
1380+
Report("HINT: Is mach_vm_region_recurse allowed by sandbox?\n");
1381+
}
1382+
1383+
return (kr == KERN_SUCCESS && addr >= address && addr < address + vmsize);
1384+
}
1385+
13631386
// FIXME implement on this platform.
13641387
void GetMemoryProfile(fill_profile_f cb, uptr *stats) {}
13651388

compiler-rt/lib/sanitizer_common/sanitizer_mac.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,8 @@ struct ThreadEventCallbacks {
7676

7777
void InstallPthreadIntrospectionHook(const ThreadEventCallbacks &callbacks);
7878

79+
bool IsAddressInMappedRegion(uptr addr);
80+
7981
} // namespace __sanitizer
8082

8183
#endif // SANITIZER_APPLE

compiler-rt/lib/tsan/rtl/tsan_platform_mac.cpp

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -226,9 +226,19 @@ static void ThreadTerminateCallback(uptr thread) {
226226
void InitializePlatformEarly() {
227227
# if !SANITIZER_GO && SANITIZER_IOS
228228
uptr max_vm = GetMaxUserVirtualAddress() + 1;
229-
if (max_vm != HiAppMemEnd()) {
230-
Printf("ThreadSanitizer: unsupported vm address limit %p, expected %p.\n",
231-
(void *)max_vm, (void *)HiAppMemEnd());
229+
if (max_vm < HiAppMemEnd()) {
230+
Report(
231+
"ThreadSanitizer: Unsupported virtual memory layout:\n\tVM address "
232+
"limit = %p\n\tExpected %p.\n",
233+
(void*)max_vm, (void*)HiAppMemEnd());
234+
Die();
235+
}
236+
// In some configurations, the max_vm is expanded, but much of this space is
237+
// already mapped. TSAN will not work in this configuration.
238+
if (IsAddressInMappedRegion(HiAppMemEnd() - 1)) {
239+
Report(
240+
"ThreadSanitizer: Unsupported virtual memory layout: Address %p is "
241+
"already mapped.\n");
232242
Die();
233243
}
234244
#endif

0 commit comments

Comments
 (0)