[llvm] 56bf960 - [CMake] Enable building with UBSAN + clang-cl on windows.

Pierre Gousseau via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 13 02:17:58 PDT 2023


Author: Pierre Gousseau
Date: 2023-06-13T10:17:49+01:00
New Revision: 56bf960629cb5accf0584b1aabb1a4d8191249d1

URL: https://github.com/llvm/llvm-project/commit/56bf960629cb5accf0584b1aabb1a4d8191249d1
DIFF: https://github.com/llvm/llvm-project/commit/56bf960629cb5accf0584b1aabb1a4d8191249d1.diff

LOG: [CMake] Enable building with UBSAN + clang-cl on windows.

Currently both ASAN and UBSAN are supported on Windows but only ASAN is enabled in LLVM build system. This patch enables the option to build LLVM with UBSAN on windows.

Tested with clang-cl released in LLVM16.

Submitting on behalf of @dwang.

Reviewed by: andrewng, pgousseau

Differential Revision: https://reviews.llvm.org/D151511

Added: 
    

Modified: 
    llvm/cmake/modules/HandleLLVMOptions.cmake
    llvm/include/llvm/ADT/EpochTracker.h
    llvm/include/llvm/ADT/SmallPtrSet.h
    llvm/include/llvm/ADT/StringMap.h
    llvm/include/llvm/Support/AllocatorBase.h

Removed: 
    


################################################################################
diff  --git a/llvm/cmake/modules/HandleLLVMOptions.cmake b/llvm/cmake/modules/HandleLLVMOptions.cmake
index 1c63db51a692b..525ba48850ca7 100644
--- a/llvm/cmake/modules/HandleLLVMOptions.cmake
+++ b/llvm/cmake/modules/HandleLLVMOptions.cmake
@@ -849,7 +849,7 @@ if (LLVM_COMPILER_IS_GCC_COMPATIBLE AND NOT LLVM_ENABLE_WARNINGS)
 endif()
 
 macro(append_common_sanitizer_flags)
-  if (NOT MSVC)
+  if (NOT MSVC OR CLANG_CL)
     # Append -fno-omit-frame-pointer and turn on debug info to get better
     # stack traces.
     add_flag_if_supported("-fno-omit-frame-pointer" FNO_OMIT_FRAME_POINTER)
@@ -928,23 +928,18 @@ if(LLVM_USE_SANITIZER)
       message(FATAL_ERROR "This sanitizer not yet supported in a MinGW environment: ${LLVM_USE_SANITIZER}")
     endif()
   elseif(MSVC)
-    if (LLVM_USE_SANITIZER STREQUAL "Address")
-      append_common_sanitizer_flags()
-      append("/fsanitize=address" CMAKE_C_FLAGS CMAKE_CXX_FLAGS)
-      if (NOT CLANG_CL)
-        # Not compatible with /RTC flags.
-        foreach (flags_opt_to_scrub
-            CMAKE_CXX_FLAGS_${uppercase_CMAKE_BUILD_TYPE} CMAKE_C_FLAGS_${uppercase_CMAKE_BUILD_TYPE})
-          string (REGEX REPLACE "(^| )/RTC[1csu]*($| )" " "
-            "${flags_opt_to_scrub}" "${${flags_opt_to_scrub}}")
-        endforeach()
+    if (NOT LLVM_USE_SANITIZER MATCHES "^(Address|Undefined|Address;Undefined|Undefined;Address)$")
+      message(FATAL_ERROR "This sanitizer not yet supported in the MSVC environment: ${LLVM_USE_SANITIZER}")
+    endif()
+    append_common_sanitizer_flags()
+    if (LINKER_IS_LLD_LINK)
+      if (LLVM_HOST_TRIPLE MATCHES "i[2-6]86-.*")
+        set(arch "i386")
+      else()
+        set(arch "x86_64")
       endif()
-      if (LINKER_IS_LLD_LINK)
-        if (LLVM_HOST_TRIPLE MATCHES "i[2-6]86-.*")
-          set(arch "i386")
-        else()
-          set(arch "x86_64")
-        endif()
+      # Prepare ASAN runtime if needed
+      if (LLVM_USE_SANITIZER MATCHES ".*Address.*")
         if (${LLVM_USE_CRT_${uppercase_CMAKE_BUILD_TYPE}} MATCHES "^(MT|MTd)$")
           append("/wholearchive:clang_rt.asan-${arch}.lib /wholearchive:clang_rt.asan_cxx-${arch}.lib"
             CMAKE_EXE_LINKER_FLAGS)
@@ -955,8 +950,25 @@ if(LLVM_USE_SANITIZER)
             CMAKE_EXE_LINKER_FLAGS CMAKE_MODULE_LINKER_FLAGS CMAKE_SHARED_LINKER_FLAGS)
         endif()
       endif()
-    else()
-      message(FATAL_ERROR "This sanitizer not yet supported in the MSVC environment: ${LLVM_USE_SANITIZER}")
+    endif()
+    if (LLVM_USE_SANITIZER MATCHES ".*Address.*")
+      if (NOT CLANG_CL)
+        append("/fsanitize=address" CMAKE_C_FLAGS CMAKE_CXX_FLAGS)
+        # Not compatible with /RTC flags.
+        foreach (flags_opt_to_scrub
+            CMAKE_CXX_FLAGS_${uppercase_CMAKE_BUILD_TYPE} CMAKE_C_FLAGS_${uppercase_CMAKE_BUILD_TYPE})
+          string (REGEX REPLACE "(^| )/RTC[1csu]*($| )" " "
+            "${flags_opt_to_scrub}" "${${flags_opt_to_scrub}}")
+        endforeach()
+      else()
+        append("-fsanitize=address" CMAKE_C_FLAGS CMAKE_CXX_FLAGS)
+      endif()
+    endif()
+    if (LLVM_USE_SANITIZER MATCHES ".*Undefined.*")
+      if (NOT CLANG_CL)
+        message(FATAL_ERROR "This sanitizer is only supported by clang-cl: Undefined")
+      endif()
+      append(${LLVM_UBSAN_FLAGS} CMAKE_C_FLAGS CMAKE_CXX_FLAGS)
     endif()
   else()
     message(FATAL_ERROR "LLVM_USE_SANITIZER is not supported on this platform.")

diff  --git a/llvm/include/llvm/ADT/EpochTracker.h b/llvm/include/llvm/ADT/EpochTracker.h
index a639d1b5b3ec4..fc41d6f2c92d2 100644
--- a/llvm/include/llvm/ADT/EpochTracker.h
+++ b/llvm/include/llvm/ADT/EpochTracker.h
@@ -23,6 +23,7 @@
 namespace llvm {
 
 #if LLVM_ENABLE_ABI_BREAKING_CHECKS
+#define LLVM_DEBUGEPOCHBASE_HANDLEBASE_EMPTYBASE
 
 /// A base class for data structure classes wishing to make iterators
 /// ("handles") pointing into themselves fail-fast.  When building without
@@ -78,6 +79,11 @@ class DebugEpochBase {
 };
 
 #else
+#ifdef _MSC_VER
+#define LLVM_DEBUGEPOCHBASE_HANDLEBASE_EMPTYBASE __declspec(empty_bases)
+#else
+#define LLVM_DEBUGEPOCHBASE_HANDLEBASE_EMPTYBASE
+#endif // _MSC_VER
 
 class DebugEpochBase {
 public:

diff  --git a/llvm/include/llvm/ADT/SmallPtrSet.h b/llvm/include/llvm/ADT/SmallPtrSet.h
index 3d8191b3d1621..4c064397057d3 100644
--- a/llvm/include/llvm/ADT/SmallPtrSet.h
+++ b/llvm/include/llvm/ADT/SmallPtrSet.h
@@ -264,8 +264,9 @@ class SmallPtrSetIteratorImpl {
 
 /// SmallPtrSetIterator - This implements a const_iterator for SmallPtrSet.
 template <typename PtrTy>
-class SmallPtrSetIterator : public SmallPtrSetIteratorImpl,
-                            DebugEpochBase::HandleBase {
+class LLVM_DEBUGEPOCHBASE_HANDLEBASE_EMPTYBASE SmallPtrSetIterator
+    : public SmallPtrSetIteratorImpl,
+      DebugEpochBase::HandleBase {
   using PtrTraits = PointerLikeTypeTraits<PtrTy>;
 
 public:

diff  --git a/llvm/include/llvm/ADT/StringMap.h b/llvm/include/llvm/ADT/StringMap.h
index 17e81bcc2ab94..466f95254d102 100644
--- a/llvm/include/llvm/ADT/StringMap.h
+++ b/llvm/include/llvm/ADT/StringMap.h
@@ -107,8 +107,9 @@ class StringMapImpl {
 /// funky memory allocation and hashing things to make it extremely efficient,
 /// storing the string data *after* the value in the map.
 template <typename ValueTy, typename AllocatorTy = MallocAllocator>
-class StringMap : public StringMapImpl,
-                  private detail::AllocatorHolder<AllocatorTy> {
+class LLVM_ALLOCATORHOLDER_EMPTYBASE StringMap
+    : public StringMapImpl,
+      private detail::AllocatorHolder<AllocatorTy> {
   using AllocTy = detail::AllocatorHolder<AllocatorTy>;
 
 public:

diff  --git a/llvm/include/llvm/Support/AllocatorBase.h b/llvm/include/llvm/Support/AllocatorBase.h
index 278ec434d384c..0442432250069 100644
--- a/llvm/include/llvm/Support/AllocatorBase.h
+++ b/llvm/include/llvm/Support/AllocatorBase.h
@@ -19,6 +19,12 @@
 #ifndef LLVM_SUPPORT_ALLOCATORBASE_H
 #define LLVM_SUPPORT_ALLOCATORBASE_H
 
+#ifdef _MSC_VER
+#define LLVM_ALLOCATORHOLDER_EMPTYBASE __declspec(empty_bases)
+#else
+#define LLVM_ALLOCATORHOLDER_EMPTYBASE
+#endif // _MSC_VER
+
 #include "llvm/Support/Compiler.h"
 #include "llvm/Support/MemAlloc.h"
 #include <type_traits>


        


More information about the llvm-commits mailing list