[compiler-rt] [compiler-rt][rtsan] Introduce rtsan_interface.h and ScopedDisabler (PR #106736)
Chris Apple via llvm-commits
llvm-commits at lists.llvm.org
Fri Sep 6 11:46:19 PDT 2024
https://github.com/cjappl updated https://github.com/llvm/llvm-project/pull/106736
>From fc1aad5c903d63b6652b68626facf68c04841786 Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Thu, 29 Aug 2024 17:17:12 -0700
Subject: [PATCH 1/7] [compiler-rt][rtsan] Introduce rtsan_interface.h and
ScopedDisabler
---
compiler-rt/include/CMakeLists.txt | 1 +
.../include/sanitizer/rtsan_interface.h | 115 ++++++++++++++++++
compiler-rt/lib/rtsan/rtsan.h | 20 +--
compiler-rt/test/rtsan/disabler.cpp | 35 ++++++
compiler-rt/test/rtsan/enabler.cpp | 35 ++++++
5 files changed, 192 insertions(+), 14 deletions(-)
create mode 100644 compiler-rt/include/sanitizer/rtsan_interface.h
create mode 100644 compiler-rt/test/rtsan/disabler.cpp
create mode 100644 compiler-rt/test/rtsan/enabler.cpp
diff --git a/compiler-rt/include/CMakeLists.txt b/compiler-rt/include/CMakeLists.txt
index d598a94ee2e237..242d62b9b447b1 100644
--- a/compiler-rt/include/CMakeLists.txt
+++ b/compiler-rt/include/CMakeLists.txt
@@ -10,6 +10,7 @@ if (COMPILER_RT_BUILD_SANITIZERS)
sanitizer/lsan_interface.h
sanitizer/msan_interface.h
sanitizer/netbsd_syscall_hooks.h
+ sanitizer/rtsan_interface.h
sanitizer/scudo_interface.h
sanitizer/tsan_interface.h
sanitizer/tsan_interface_atomic.h
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
new file mode 100644
index 00000000000000..399cbfd294dacd
--- /dev/null
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -0,0 +1,115 @@
+//===-- sanitizer/rtsan_interface.h -----------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This file is a part of RealtimeSanitizer.
+//
+// Public interface header.
+//===----------------------------------------------------------------------===//
+
+#ifndef SANITIZER_RTSAN_INTERFACE_H
+#define SANITIZER_RTSAN_INTERFACE_H
+
+#if __has_include(<sanitizer/common_interface_defs.h>)
+#include <sanitizer/common_interface_defs.h>
+#else
+#define SANITIZER_CDECL
+#endif // __has_include(<sanitizer/common_interface_defs.h>)
+
+#ifdef __cplusplus
+extern "C" {
+#endif // __cplusplus
+
+// Initializes rtsan if it has not been initialized yet.
+// Used by the RTSan runtime to ensure that rtsan is initialized before any
+// other rtsan functions are called.
+void SANITIZER_CDECL __rtsan_ensure_initialized();
+
+// Enter real-time context.
+// When in a real-time context, RTSan interceptors will error if realtime
+// violations are detected. Calls to this method are injected at the code
+// generation stage when RTSan is enabled.
+void SANITIZER_CDECL __rtsan_realtime_enter();
+
+// Exit the real-time context.
+// When not in a real-time context, RTSan interceptors will simply forward
+// intercepted method calls to the real methods.
+void SANITIZER_CDECL __rtsan_realtime_exit();
+
+// Disable all RTSan error reporting.
+void SANITIZER_CDECL __rtsan_disable(void);
+
+// Re-enable all RTSan error reporting.
+// The counterpart to `__rtsan_disable`.
+void SANITIZER_CDECL __rtsan_enable(void);
+
+// Expect that the next call to a function with the given name will not be
+// called from a realtime context.
+void SANITIZER_CDECL
+__rtsan_expect_not_realtime(const char *intercepted_function_name);
+
+#ifdef __cplusplus
+} // extern "C"
+
+namespace __rtsan {
+#if defined(__has_feature) && __has_feature(realtime_sanitizer)
+
+void Initialize() { __rtsan_ensure_initialized(); }
+
+class ScopedEnabler {
+public:
+ ScopedEnabler() { __rtsan_realtime_enter(); }
+ ~ScopedEnabler() { __rtsan_realtime_exit(); }
+
+#if __cplusplus >= 201103L
+ ScopedEnabler(const ScopedEnabler &) = delete;
+ ScopedEnabler &operator=(const ScopedEnabler &) = delete;
+ ScopedEnabler(ScopedEnabler &&) = delete;
+ ScopedEnabler &operator=(ScopedEnabler &&) = delete;
+#else
+private:
+ ScopedEnabler(const ScopedEnabler &);
+ ScopedEnabler &operator=(const ScopedEnabler &);
+#endif // __cplusplus >= 201103L
+};
+
+class ScopedDisabler {
+public:
+ ScopedDisabler() { __rtsan_disable(); }
+ ~ScopedDisabler() { __rtsan_enable(); }
+
+#if __cplusplus >= 201103L
+ ScopedDisabler(const ScopedDisabler &) = delete;
+ ScopedDisabler &operator=(const ScopedDisabler &) = delete;
+ ScopedDisabler(ScopedDisabler &&) = delete;
+ ScopedDisabler &operator=(ScopedDisabler &&) = delete;
+#else
+private:
+ ScopedDisabler(const ScopedDisabler &);
+ ScopedDisabler &operator=(const ScopedDisabler &);
+#endif // __cplusplus >= 201103L
+};
+
+#else // doesn't have realtime_sanitizer
+
+void Initialize() {}
+
+class ScopedEnabler {
+public:
+ ScopedEnabler() {}
+};
+
+class ScopedDisabler {
+public:
+ ScopedDisabler() {}
+};
+
+#endif // defined(__has_feature) && __has_feature(realtime_sanitizer)
+} // namespace __rtsan
+#endif // __cplusplus
+
+#endif // SANITIZER_RTSAN_INTERFACE_H
diff --git a/compiler-rt/lib/rtsan/rtsan.h b/compiler-rt/lib/rtsan/rtsan.h
index ae23609f97d2dc..80fcb1dec2ff1c 100644
--- a/compiler-rt/lib/rtsan/rtsan.h
+++ b/compiler-rt/lib/rtsan/rtsan.h
@@ -18,32 +18,24 @@ extern "C" {
// A call to this method is added to the preinit array on Linux systems.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_init();
-// Initializes rtsan if it has not been initialized yet.
-// Used by the RTSan runtime to ensure that rtsan is initialized before any
-// other rtsan functions are called.
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_ensure_initialized();
SANITIZER_INTERFACE_ATTRIBUTE bool __rtsan_is_initialized();
-// Enter real-time context.
-// When in a real-time context, RTSan interceptors will error if realtime
-// violations are detected. Calls to this method are injected at the code
-// generation stage when RTSan is enabled.
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_realtime_enter();
-// Exit the real-time context.
-// When not in a real-time context, RTSan interceptors will simply forward
-// intercepted method calls to the real methods.
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_realtime_exit();
-// Disable all RTSan error reporting.
-// Injected into the code if "nosanitize(realtime)" is on a function.
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_disable();
-// Re-enable all RTSan error reporting.
-// The counterpart to `__rtsan_disable`.
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_enable();
+// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void
__rtsan_expect_not_realtime(const char *intercepted_function_name);
diff --git a/compiler-rt/test/rtsan/disabler.cpp b/compiler-rt/test/rtsan/disabler.cpp
new file mode 100644
index 00000000000000..1fc14b0bac4e01
--- /dev/null
+++ b/compiler-rt/test/rtsan/disabler.cpp
@@ -0,0 +1,35 @@
+// RUN: %clangxx -fsanitize=realtime %s -o %t
+// RUN: not %run %t 2>&1 | FileCheck %s
+// RUN: %clangxx %s -fsanitize=realtime -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
+// RUN: %clangxx %s -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-DISABLED-IR
+// UNSUPPORTED: ios
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "sanitizer/rtsan_interface.h"
+
+void violation() [[clang::nonblocking]] {
+ void *ptr;
+ {
+ __rtsan::ScopedDisabler disabler{};
+ ptr = malloc(2);
+ printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
+ }
+
+ free(ptr);
+}
+
+int main() {
+ violation();
+ return 0;
+ // CHECK: {{.*Real-time violation.*}}
+ // CHECK-NOT: {{.*malloc*}}
+ // CHECK: {{.*free*}}
+}
+
+// CHECK-ENABLED-IR: {{.*@__rtsan_disable.*}}
+// CHECK-ENABLED-IR: {{.*@__rtsan_enable.*}}
+
+// CHECK-DISABLED-IR-NOT: {{.*__rtsan_disable.*}}
+// CHECK-DISABLED-IR-NOT: {{.*__rtsan_enable.*}}
diff --git a/compiler-rt/test/rtsan/enabler.cpp b/compiler-rt/test/rtsan/enabler.cpp
new file mode 100644
index 00000000000000..0ae8ba6e792839
--- /dev/null
+++ b/compiler-rt/test/rtsan/enabler.cpp
@@ -0,0 +1,35 @@
+// RUN: %clangxx -fsanitize=realtime %s -o %t
+// RUN: not %run %t 2>&1 | FileCheck %s
+// RUN: %clangxx %s -fsanitize=realtime -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
+// RUN: %clangxx %s -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-DISABLED-IR
+// UNSUPPORTED: ios
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "sanitizer/rtsan_interface.h"
+
+void violation() {
+ void *ptr = malloc(2);
+ ptr = malloc(2);
+ printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
+
+ {
+ __rtsan::ScopedEnabler rtsan{};
+ free(ptr);
+ }
+}
+
+int main() {
+ violation();
+ return 0;
+ // CHECK: {{.*Real-time violation.*}}
+ // CHECK-NOT: {{.*malloc*}}
+ // CHECK: {{.*free*}}
+}
+
+// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_enter.*}}
+// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_exit.*}}
+
+// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_enter.*}}
+// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_exit.*}}
>From bed7e12d2fb5c0221b247f4da124baecc549844c Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Fri, 30 Aug 2024 08:20:03 -0700
Subject: [PATCH 2/7] Add rtsan_enabled define
---
compiler-rt/include/sanitizer/rtsan_interface.h | 6 ++++--
compiler-rt/test/rtsan/enabler.cpp | 7 +++++--
2 files changed, 9 insertions(+), 4 deletions(-)
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
index 399cbfd294dacd..b816d5a8b419ee 100644
--- a/compiler-rt/include/sanitizer/rtsan_interface.h
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -56,7 +56,8 @@ __rtsan_expect_not_realtime(const char *intercepted_function_name);
} // extern "C"
namespace __rtsan {
-#if defined(__has_feature) && __has_feature(realtime_sanitizer)
+#if (defined(__has_feature) && __has_feature(realtime_sanitizer)) || \
+ defined(RTSAN_ENABLED)
void Initialize() { __rtsan_ensure_initialized(); }
@@ -108,7 +109,8 @@ class ScopedDisabler {
ScopedDisabler() {}
};
-#endif // defined(__has_feature) && __has_feature(realtime_sanitizer)
+#endif // defined(__has_feature) && __has_feature(realtime_sanitizer) ||
+ // defined(RTSAN_ENABLED)
} // namespace __rtsan
#endif // __cplusplus
diff --git a/compiler-rt/test/rtsan/enabler.cpp b/compiler-rt/test/rtsan/enabler.cpp
index 0ae8ba6e792839..f26116ba274e5f 100644
--- a/compiler-rt/test/rtsan/enabler.cpp
+++ b/compiler-rt/test/rtsan/enabler.cpp
@@ -1,6 +1,6 @@
-// RUN: %clangxx -fsanitize=realtime %s -o %t
+// RUN: %clangxx -DRTSAN_ENABLED -fsanitize=realtime %s -o %t
// RUN: not %run %t 2>&1 | FileCheck %s
-// RUN: %clangxx %s -fsanitize=realtime -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
+// RUN: %clangxx %s -DRTSAN_ENABLED -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
// RUN: %clangxx %s -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-DISABLED-IR
// UNSUPPORTED: ios
@@ -21,6 +21,7 @@ void violation() {
}
int main() {
+ __rtsan::Initialize();
violation();
return 0;
// CHECK: {{.*Real-time violation.*}}
@@ -28,8 +29,10 @@ int main() {
// CHECK: {{.*free*}}
}
+// CHECK-ENABLED-IR: {{.*__rtsan_ensure_initialized.*}}
// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_enter.*}}
// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_exit.*}}
+// CHECK-DISABLED-IR-NOT: {{.*__rtsan_ensure_initialized.*}}
// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_enter.*}}
// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_exit.*}}
>From 5f91c56e53eed6b0ce6020e8f3086781a34b28db Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Fri, 30 Aug 2024 08:33:57 -0700
Subject: [PATCH 3/7] Tweaked name of macro
---
compiler-rt/include/sanitizer/rtsan_interface.h | 6 +++---
compiler-rt/test/rtsan/enabler.cpp | 4 ++--
2 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
index b816d5a8b419ee..a32ba94aad453c 100644
--- a/compiler-rt/include/sanitizer/rtsan_interface.h
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -57,7 +57,7 @@ __rtsan_expect_not_realtime(const char *intercepted_function_name);
namespace __rtsan {
#if (defined(__has_feature) && __has_feature(realtime_sanitizer)) || \
- defined(RTSAN_ENABLED)
+ SANITIZE_REALTIME
void Initialize() { __rtsan_ensure_initialized(); }
@@ -109,8 +109,8 @@ class ScopedDisabler {
ScopedDisabler() {}
};
-#endif // defined(__has_feature) && __has_feature(realtime_sanitizer) ||
- // defined(RTSAN_ENABLED)
+#endif // (defined(__has_feature) && __has_feature(realtime_sanitizer)) ||
+ // SANITIZE_REALTIME
} // namespace __rtsan
#endif // __cplusplus
diff --git a/compiler-rt/test/rtsan/enabler.cpp b/compiler-rt/test/rtsan/enabler.cpp
index f26116ba274e5f..68f37276ed2462 100644
--- a/compiler-rt/test/rtsan/enabler.cpp
+++ b/compiler-rt/test/rtsan/enabler.cpp
@@ -1,6 +1,6 @@
-// RUN: %clangxx -DRTSAN_ENABLED -fsanitize=realtime %s -o %t
+// RUN: %clangxx -DSANITIZE_REALTIME=1 -fsanitize=realtime %s -o %t
// RUN: not %run %t 2>&1 | FileCheck %s
-// RUN: %clangxx %s -DRTSAN_ENABLED -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
+// RUN: %clangxx %s -DSANITIZE_REALTIME=1 -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
// RUN: %clangxx %s -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-DISABLED-IR
// UNSUPPORTED: ios
>From 218b520a347ee895c57b740dc6b17f313be32222 Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Mon, 2 Sep 2024 08:50:34 -0700
Subject: [PATCH 4/7] [PR] david - get rid of scoped enabler, macro, simplify
interface
---
.../include/sanitizer/rtsan_interface.h | 53 +------------------
compiler-rt/lib/rtsan/rtsan.h | 16 ++++--
compiler-rt/test/rtsan/enabler.cpp | 38 -------------
3 files changed, 14 insertions(+), 93 deletions(-)
delete mode 100644 compiler-rt/test/rtsan/enabler.cpp
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
index a32ba94aad453c..875e76b66eac3d 100644
--- a/compiler-rt/include/sanitizer/rtsan_interface.h
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -24,22 +24,6 @@
extern "C" {
#endif // __cplusplus
-// Initializes rtsan if it has not been initialized yet.
-// Used by the RTSan runtime to ensure that rtsan is initialized before any
-// other rtsan functions are called.
-void SANITIZER_CDECL __rtsan_ensure_initialized();
-
-// Enter real-time context.
-// When in a real-time context, RTSan interceptors will error if realtime
-// violations are detected. Calls to this method are injected at the code
-// generation stage when RTSan is enabled.
-void SANITIZER_CDECL __rtsan_realtime_enter();
-
-// Exit the real-time context.
-// When not in a real-time context, RTSan interceptors will simply forward
-// intercepted method calls to the real methods.
-void SANITIZER_CDECL __rtsan_realtime_exit();
-
// Disable all RTSan error reporting.
void SANITIZER_CDECL __rtsan_disable(void);
@@ -47,36 +31,11 @@ void SANITIZER_CDECL __rtsan_disable(void);
// The counterpart to `__rtsan_disable`.
void SANITIZER_CDECL __rtsan_enable(void);
-// Expect that the next call to a function with the given name will not be
-// called from a realtime context.
-void SANITIZER_CDECL
-__rtsan_expect_not_realtime(const char *intercepted_function_name);
-
#ifdef __cplusplus
} // extern "C"
namespace __rtsan {
-#if (defined(__has_feature) && __has_feature(realtime_sanitizer)) || \
- SANITIZE_REALTIME
-
-void Initialize() { __rtsan_ensure_initialized(); }
-
-class ScopedEnabler {
-public:
- ScopedEnabler() { __rtsan_realtime_enter(); }
- ~ScopedEnabler() { __rtsan_realtime_exit(); }
-
-#if __cplusplus >= 201103L
- ScopedEnabler(const ScopedEnabler &) = delete;
- ScopedEnabler &operator=(const ScopedEnabler &) = delete;
- ScopedEnabler(ScopedEnabler &&) = delete;
- ScopedEnabler &operator=(ScopedEnabler &&) = delete;
-#else
-private:
- ScopedEnabler(const ScopedEnabler &);
- ScopedEnabler &operator=(const ScopedEnabler &);
-#endif // __cplusplus >= 201103L
-};
+#if defined(__has_feature) && __has_feature(realtime_sanitizer)
class ScopedDisabler {
public:
@@ -97,20 +56,12 @@ class ScopedDisabler {
#else // doesn't have realtime_sanitizer
-void Initialize() {}
-
-class ScopedEnabler {
-public:
- ScopedEnabler() {}
-};
-
class ScopedDisabler {
public:
ScopedDisabler() {}
};
-#endif // (defined(__has_feature) && __has_feature(realtime_sanitizer)) ||
- // SANITIZE_REALTIME
+#endif // defined(__has_feature) && __has_feature(realtime_sanitizer)
} // namespace __rtsan
#endif // __cplusplus
diff --git a/compiler-rt/lib/rtsan/rtsan.h b/compiler-rt/lib/rtsan/rtsan.h
index 80fcb1dec2ff1c..68f875164af8f6 100644
--- a/compiler-rt/lib/rtsan/rtsan.h
+++ b/compiler-rt/lib/rtsan/rtsan.h
@@ -18,15 +18,22 @@ extern "C" {
// A call to this method is added to the preinit array on Linux systems.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_init();
-// See documentation in rtsan_interface.h.
+// Initializes rtsan if it has not been initialized yet.
+// Used by the RTSan runtime to ensure that rtsan is initialized before any
+// other rtsan functions are called.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_ensure_initialized();
SANITIZER_INTERFACE_ATTRIBUTE bool __rtsan_is_initialized();
-// See documentation in rtsan_interface.h.
+// Enter real-time context.
+// When in a real-time context, RTSan interceptors will error if realtime
+// violations are detected. Calls to this method are injected at the code
+// generation stage when RTSan is enabled.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_realtime_enter();
-// See documentation in rtsan_interface.h.
+// Exit the real-time context.
+// When not in a real-time context, RTSan interceptors will simply forward
+// intercepted method calls to the real methods.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_realtime_exit();
// See documentation in rtsan_interface.h.
@@ -35,7 +42,8 @@ SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_disable();
// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_enable();
-// See documentation in rtsan_interface.h.
+// Expect that the next call to a function with the given name will not be
+// called from a realtime context.
SANITIZER_INTERFACE_ATTRIBUTE void
__rtsan_expect_not_realtime(const char *intercepted_function_name);
diff --git a/compiler-rt/test/rtsan/enabler.cpp b/compiler-rt/test/rtsan/enabler.cpp
deleted file mode 100644
index 68f37276ed2462..00000000000000
--- a/compiler-rt/test/rtsan/enabler.cpp
+++ /dev/null
@@ -1,38 +0,0 @@
-// RUN: %clangxx -DSANITIZE_REALTIME=1 -fsanitize=realtime %s -o %t
-// RUN: not %run %t 2>&1 | FileCheck %s
-// RUN: %clangxx %s -DSANITIZE_REALTIME=1 -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-ENABLED-IR
-// RUN: %clangxx %s -o - -S -emit-llvm | FileCheck %s --check-prefix=CHECK-DISABLED-IR
-// UNSUPPORTED: ios
-
-#include <stdio.h>
-#include <stdlib.h>
-
-#include "sanitizer/rtsan_interface.h"
-
-void violation() {
- void *ptr = malloc(2);
- ptr = malloc(2);
- printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
-
- {
- __rtsan::ScopedEnabler rtsan{};
- free(ptr);
- }
-}
-
-int main() {
- __rtsan::Initialize();
- violation();
- return 0;
- // CHECK: {{.*Real-time violation.*}}
- // CHECK-NOT: {{.*malloc*}}
- // CHECK: {{.*free*}}
-}
-
-// CHECK-ENABLED-IR: {{.*__rtsan_ensure_initialized.*}}
-// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_enter.*}}
-// CHECK-ENABLED-IR: {{.*@__rtsan_realtime_exit.*}}
-
-// CHECK-DISABLED-IR-NOT: {{.*__rtsan_ensure_initialized.*}}
-// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_enter.*}}
-// CHECK-DISABLED-IR-NOT: {{.*__rtsan_realtime_exit.*}}
>From ec206964c01585d4addaa26e3d4105d2239f55a5 Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Mon, 2 Sep 2024 08:51:28 -0700
Subject: [PATCH 5/7] Improve docs of rtsan enable/disable
---
compiler-rt/include/sanitizer/rtsan_interface.h | 5 +++--
compiler-rt/lib/rtsan/rtsan.h | 2 --
2 files changed, 3 insertions(+), 4 deletions(-)
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
index 875e76b66eac3d..edff161d74b4e5 100644
--- a/compiler-rt/include/sanitizer/rtsan_interface.h
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -25,10 +25,11 @@ extern "C" {
#endif // __cplusplus
// Disable all RTSan error reporting.
+// Must be paired with a call to `__rtsan_enable`
void SANITIZER_CDECL __rtsan_disable(void);
// Re-enable all RTSan error reporting.
-// The counterpart to `__rtsan_disable`.
+// Must follow a call to `__rtsan_disable`.
void SANITIZER_CDECL __rtsan_enable(void);
#ifdef __cplusplus
@@ -54,7 +55,7 @@ class ScopedDisabler {
#endif // __cplusplus >= 201103L
};
-#else // doesn't have realtime_sanitizer
+#else
class ScopedDisabler {
public:
diff --git a/compiler-rt/lib/rtsan/rtsan.h b/compiler-rt/lib/rtsan/rtsan.h
index 68f875164af8f6..ca72d41d11125c 100644
--- a/compiler-rt/lib/rtsan/rtsan.h
+++ b/compiler-rt/lib/rtsan/rtsan.h
@@ -42,8 +42,6 @@ SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_disable();
// See documentation in rtsan_interface.h.
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_enable();
-// Expect that the next call to a function with the given name will not be
-// called from a realtime context.
SANITIZER_INTERFACE_ATTRIBUTE void
__rtsan_expect_not_realtime(const char *intercepted_function_name);
>From 50f3672bbac09b902f8449d64aca5dfa1e8cb9ca Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Fri, 6 Sep 2024 10:54:49 -0700
Subject: [PATCH 6/7] [PR] vitalybuka - nested disabler test
---
compiler-rt/test/rtsan/disabler.cpp | 17 ++++++++++++++++-
1 file changed, 16 insertions(+), 1 deletion(-)
diff --git a/compiler-rt/test/rtsan/disabler.cpp b/compiler-rt/test/rtsan/disabler.cpp
index 1fc14b0bac4e01..4101a756b803ba 100644
--- a/compiler-rt/test/rtsan/disabler.cpp
+++ b/compiler-rt/test/rtsan/disabler.cpp
@@ -17,6 +17,20 @@ void violation() [[clang::nonblocking]] {
printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
}
+ // ensure nested disablers don't interfere with one another
+ void *ptr2;
+ {
+ __rtsan::ScopedDisabler disabler{};
+ {
+ __rtsan::ScopedDisabler disabler2{};
+ ptr2 = malloc(2);
+ printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
+ }
+
+ free(ptr2);
+ printf("Free'd second pointer in disabled context without crashing\n");
+ }
+
free(ptr);
}
@@ -25,7 +39,8 @@ int main() {
return 0;
// CHECK: {{.*Real-time violation.*}}
// CHECK-NOT: {{.*malloc*}}
- // CHECK: {{.*free*}}
+ // CHECK: Free'd second pointer in disabled context without crashing
+ // CHECK: {{.*real-time unsafe function `free`.*}}
}
// CHECK-ENABLED-IR: {{.*@__rtsan_disable.*}}
>From aac11a1e4eef01e2ff22f44207250bbfba759f33 Mon Sep 17 00:00:00 2001
From: Chris Apple <cja-private at pm.me>
Date: Fri, 6 Sep 2024 10:56:05 -0700
Subject: [PATCH 7/7] [PR] vitalybuka - adjusted interface, deleted
constructors and removed has_include
---
compiler-rt/include/sanitizer/rtsan_interface.h | 14 ++++++++++----
compiler-rt/test/rtsan/disabler.cpp | 15 +++++++++------
2 files changed, 19 insertions(+), 10 deletions(-)
diff --git a/compiler-rt/include/sanitizer/rtsan_interface.h b/compiler-rt/include/sanitizer/rtsan_interface.h
index edff161d74b4e5..5d7ce5345712e5 100644
--- a/compiler-rt/include/sanitizer/rtsan_interface.h
+++ b/compiler-rt/include/sanitizer/rtsan_interface.h
@@ -14,11 +14,7 @@
#ifndef SANITIZER_RTSAN_INTERFACE_H
#define SANITIZER_RTSAN_INTERFACE_H
-#if __has_include(<sanitizer/common_interface_defs.h>)
#include <sanitizer/common_interface_defs.h>
-#else
-#define SANITIZER_CDECL
-#endif // __has_include(<sanitizer/common_interface_defs.h>)
#ifdef __cplusplus
extern "C" {
@@ -60,6 +56,16 @@ class ScopedDisabler {
class ScopedDisabler {
public:
ScopedDisabler() {}
+#if __cplusplus >= 201103L
+ ScopedDisabler(const ScopedDisabler &) = delete;
+ ScopedDisabler &operator=(const ScopedDisabler &) = delete;
+ ScopedDisabler(ScopedDisabler &&) = delete;
+ ScopedDisabler &operator=(ScopedDisabler &&) = delete;
+#else
+private:
+ ScopedDisabler(const ScopedDisabler &);
+ ScopedDisabler &operator=(const ScopedDisabler &);
+#endif // __cplusplus >= 201103L
};
#endif // defined(__has_feature) && __has_feature(realtime_sanitizer)
diff --git a/compiler-rt/test/rtsan/disabler.cpp b/compiler-rt/test/rtsan/disabler.cpp
index 4101a756b803ba..0a6411a2be6945 100644
--- a/compiler-rt/test/rtsan/disabler.cpp
+++ b/compiler-rt/test/rtsan/disabler.cpp
@@ -14,21 +14,22 @@ void violation() [[clang::nonblocking]] {
{
__rtsan::ScopedDisabler disabler{};
ptr = malloc(2);
- printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
+ fprintf(stderr, "Allocated pointer %p in disabled context\n", ptr);
}
// ensure nested disablers don't interfere with one another
- void *ptr2;
{
+ void *ptr2;
__rtsan::ScopedDisabler disabler{};
{
__rtsan::ScopedDisabler disabler2{};
ptr2 = malloc(2);
- printf("ptr: %p\n", ptr); // ensure we don't optimize out the malloc
+ fprintf(stderr, "Allocated second pointer %p in disabled context\n",
+ ptr2);
}
free(ptr2);
- printf("Free'd second pointer in disabled context without crashing\n");
+ fprintf(stderr, "Free'd second pointer in disabled context\n");
}
free(ptr);
@@ -37,10 +38,12 @@ void violation() [[clang::nonblocking]] {
int main() {
violation();
return 0;
+ // CHECK: Allocated pointer {{.*}} in disabled context
+ // CHECK: Allocated second pointer {{.*}} in disabled context
+ // CHECK: Free'd second pointer in disabled context
// CHECK: {{.*Real-time violation.*}}
// CHECK-NOT: {{.*malloc*}}
- // CHECK: Free'd second pointer in disabled context without crashing
- // CHECK: {{.*real-time unsafe function `free`.*}}
+ // CHECK-NEXT: {{.*free.*}}
}
// CHECK-ENABLED-IR: {{.*@__rtsan_disable.*}}
More information about the llvm-commits
mailing list