melver wrote:

> > I guess maybe I'm not sure about the expected usage. Is the code you're 
> > trying to skip over code which performs checks, or code which instruments 
> > allocations? We could potentially have separate builtins which would return 
> > different values for those cases. The documentation doesn't clearly state 
> > which case the builtin is intended for.
> 
> It's intended for conditionally executing code that performs explicit checks 
> using the runtime's internal state. For example like so:
> 
> ```
> if (__builtin_allow_sanitize_check("thread")) { // similar for asan, msan 
>    __tsan_read8(addr);  // explicit check
> }
> asm volatile (... inline asm that accesses addr ...);
> ```
> 
> In the Linux kernel more APIs exist to let the sanitizer runtime perform 
> explicit checks given a pointer + size, but we need to skip over them if 
> we're in a context where instrumentation (be implicit or explicit) is 
> disallowed.
> 
> So it's really very similar to `__builtin_allow_runtime_check` in spirit, 
> except the runtime here is a known sanitizer and the policy when we're 
> allowed to check is much simpler for now.
> 
> If the documentation can be improved, we can certainly do so. Maybe instead 
> of "Conditional Sanitizer Checks .." it should be "Explicit Sanitizer Checks 
> .." with a more concrete example.

Perhaps something like this to clarify documentation:

```
diff --git a/clang/docs/AddressSanitizer.rst b/clang/docs/AddressSanitizer.rst
index dc0ba79f66cc..ca21b4c2f81a 100644
--- a/clang/docs/AddressSanitizer.rst
+++ b/clang/docs/AddressSanitizer.rst
@@ -254,37 +254,39 @@ AddressSanitizer also supports
 works similarly to ``__attribute__((no_sanitize("address")))``, but it also
 prevents instrumentation performed by other sanitizers.
 
-Conditional Sanitizer Checks with ``__builtin_allow_sanitize_check``
---------------------------------------------------------------------
+Explicit Sanitizer Checks with ``__builtin_allow_sanitize_check``
+-----------------------------------------------------------------
 
 The ``__builtin_allow_sanitize_check("address")`` builtin can be used to
-conditionally execute code only when AddressSanitizer is active for the current
-function (after inlining). This is particularly useful for inserting explicit,
-sanitizer-specific checks around operations like syscalls or inline assembly,
-which might otherwise be unchecked by the sanitizer.
+conditionally execute code only when AddressSanitizer checks are allowed for 
the
+current function (after inlining). This is particularly useful for inserting
+explicit, sanitizer-specific checks around operations like syscalls or inline
+assembly, which might otherwise be unchecked by the sanitizer.
 
 Example:
 
 .. code-block:: c
 
+    void __asan_load8(void *);
+
     inline __attribute__((always_inline))
-    void copy_to_device(void *addr, size_t size) {
-      if (__builtin_allow_sanitize_check("address")) {
-        // Custom checks that address range is valid.
-      }
-      // ... actual device memory copy logic, potentially a syscall ...
+    void my_helper(void *addr) {
+      if (__builtin_allow_sanitize_check("address"))
+        __asan_load8(addr);
+      // ... actual logic, e.g. inline assembly ...
+      asm volatile ("..." : : "r" (addr) : "memory");
     }
 
     void instrumented_function() {
       ...
-      copy_to_device(buf, sizeof(buf)); // checks are active
+      my_helper(buf); // checks are active
       ...
     }
 
     __attribute__((no_sanitize("address")))
     void uninstrumented_function() {
       ...
-      copy_to_device(buf, sizeof(buf)); // checks are skipped
+      my_helper(buf); // checks are skipped
       ...
     }
 
diff --git a/clang/docs/MemorySanitizer.rst b/clang/docs/MemorySanitizer.rst
index 54f88d076d36..75c112be1a09 100644
--- a/clang/docs/MemorySanitizer.rst
+++ b/clang/docs/MemorySanitizer.rst
@@ -101,37 +101,39 @@ positives and therefore should be used with care, and 
only if absolutely
 required; for example for certain code that cannot tolerate any instrumentation
 and resulting side-effects. This attribute overrides ``no_sanitize("memory")``.
 
-Conditional Sanitizer Checks with ``__builtin_allow_sanitize_check``
---------------------------------------------------------------------
+Explicit Sanitizer Checks with ``__builtin_allow_sanitize_check``
+-----------------------------------------------------------------
 
 The ``__builtin_allow_sanitize_check("memory")`` builtin can be used to
-conditionally execute code only when MemorySanitizer is active for the current
-function (after inlining). This is particularly useful for inserting explicit,
-sanitizer-specific checks around operations like syscalls or inline assembly,
-which might otherwise be unchecked by the sanitizer.
+conditionally execute code only when MemorySanitizer checks are allowed for the
+current function (after inlining). This is particularly useful for inserting
+explicit, sanitizer-specific checks around operations like syscalls or inline
+assembly, which might otherwise be unchecked by the sanitizer.
 
 Example:
 
 .. code-block:: c
 
+    void __msan_check_mem_is_initialized(const void *, size_t);
+
     inline __attribute__((always_inline))
-    void copy_to_device(void *addr, size_t size) {
-      if (__builtin_allow_sanitize_check("memory")) {
-        // Custom checks if `data` is initialized.
-      }
-      // ... actual device memory copy logic, potentially a syscall ...
+    void my_send(void *addr, size_t size) {
+      if (__builtin_allow_sanitize_check("memory"))
+        __msan_check_mem_is_initialized(addr, size);
+      // ... syscall or other logic where MSan may not see the access ...
+      send(addr, size);
     }
 
     void instrumented_function() {
       ...
-      copy_to_device(buf, sizeof(buf)); // checks are active
+      my_send(buf, sizeof(buf)); // checks are active
       ...
     }
 
     __attribute__((no_sanitize("memory")))
     void uninstrumented_function() {
       ...
-      copy_to_device(buf, sizeof(buf)); // checks are skipped
+      my_send(buf, sizeof(buf)); // checks are skipped
       ...
     }
 
diff --git a/clang/docs/ThreadSanitizer.rst b/clang/docs/ThreadSanitizer.rst
index c90d668600ec..81305b608a14 100644
--- a/clang/docs/ThreadSanitizer.rst
+++ b/clang/docs/ThreadSanitizer.rst
@@ -110,37 +110,39 @@ and only if absolutely required; for example for certain 
code that cannot
 tolerate any instrumentation and resulting side-effects. This attribute
 overrides ``no_sanitize("thread")``.
 
-Conditional Sanitizer Checks with ``__builtin_allow_sanitize_check``
---------------------------------------------------------------------
+Explicit Sanitizer Checks with ``__builtin_allow_sanitize_check``
+-----------------------------------------------------------------
 
 The ``__builtin_allow_sanitize_check("thread")`` builtin can be used to
-conditionally execute code only when ThreadSanitizer is active for the current
-function (after inlining). This is particularly useful for inserting explicit,
-sanitizer-specific checks around operations like syscalls or inline assembly,
-which might otherwise be unchecked by the sanitizer.
+conditionally execute code only when ThreadSanitizer checks are allowed for the
+current function (after inlining). This is particularly useful for inserting
+explicit, sanitizer-specific checks around operations like syscalls or inline
+assembly, which might otherwise be unchecked by the sanitizer.
 
 Example:
 
 .. code-block:: c
 
+    void __tsan_read8(void *);
+
     inline __attribute__((always_inline))
-    void copy_to_device(void *addr, size_t size) {
-      if (__builtin_allow_sanitize_check("thread")) {
-        // Custom checks that `data` is not concurrently modified.
-      }
-      // ... actual device memory copy logic, potentially a syscall ...
+    void my_helper(void *addr) {
+      if (__builtin_allow_sanitize_check("thread"))
+        __tsan_read8(addr);
+      // ... actual logic, e.g. inline assembly ...
+      asm volatile ("..." : : "r" (addr) : "memory");
     }
 
     void instrumented_function() {
       ...
-      copy_to_device(&shared_data, size); // checks are active
+      my_helper(&shared_data); // checks are active
       ...
     }
 
     __attribute__((no_sanitize("thread")))
     void uninstrumented_function() {
       ...
-      copy_to_device(&shared_data, size); // checks are skipped
+      my_helper(&shared_data); // checks are skipped
       ...
     }
 
```

https://github.com/llvm/llvm-project/pull/172030
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to