diff --git a/docs/workflow/building/coreclr/linux-instructions.md b/docs/workflow/building/coreclr/linux-instructions.md
index f5dd0693b83b2d..8e7457ff521850 100644
--- a/docs/workflow/building/coreclr/linux-instructions.md
+++ b/docs/workflow/building/coreclr/linux-instructions.md
@@ -99,3 +99,19 @@ Just like you can use specialized Docker images, you can also do any of the supp
## Create the Core_Root
The Core_Root provides one of the main ways to test your build. Full instructions on how to build it in the [CoreCLR testing doc](/docs/workflow/testing/coreclr/testing.md), and we also have a detailed guide on how to use it for your own testing in [its own dedicated doc](/docs/workflow/testing/using-corerun-and-coreroot.md).
+
+## Native Sanitizers
+
+CoreCLR can be built with native sanitizers like AddressSanitizer to help catch memory safety issues. To build the project with native sanitizers, add the `-fsanitize address` argument to the build script like the following:
+
+```bash
+build.sh -s clr -fsanitize address
+```
+
+When building the repo with any native sanitizers, you should build all native components in the repo with the same set of sanitizers.
+
+The following sanitizers are supported for CoreCLR on Linux:
+
+| Sanitizer Name | `-fsanitize` argument | Support Status |
+|-----------------|-----------------------|----------------|
+| AddressSanitize | `address` | regularly tested on x64 |
diff --git a/docs/workflow/building/coreclr/macos-instructions.md b/docs/workflow/building/coreclr/macos-instructions.md
index df55d204205370..8deaf4578bccef 100644
--- a/docs/workflow/building/coreclr/macos-instructions.md
+++ b/docs/workflow/building/coreclr/macos-instructions.md
@@ -32,3 +32,19 @@ It is possible to get a macOS ARM64 build using an Intel x64 Mac and vice versa,
## Create the Core_Root
The Core_Root provides one of the main ways to test your build. Full instructions on how to build it in the [CoreCLR testing doc](/docs/workflow/testing/coreclr/testing.md), and we also have a detailed guide on how to use it for your own testing in [its own dedicated doc](/docs/workflow/testing/using-corerun-and-coreroot.md).
+
+## Native Sanitizers
+
+CoreCLR can be built with native sanitizers like AddressSanitizer to help catch memory safety issues. To build the project with native sanitizers, add the `-fsanitize address` argument to the build script like the following:
+
+```bash
+build.sh -s clr -fsanitize address
+```
+
+When building the repo with any native sanitizers, you should build all native components in the repo with the same set of sanitizers.
+
+The following sanitizers are supported for CoreCLR on macOS:
+
+| Sanitizer Name | `-fsanitize` argument | Support Status |
+|-----------------|-----------------------|----------------|
+| AddressSanitize | `address` | regularly tested on x64 |
diff --git a/docs/workflow/building/coreclr/nativeaot.md b/docs/workflow/building/coreclr/nativeaot.md
index f13368867afc57..31783578b9fde0 100644
--- a/docs/workflow/building/coreclr/nativeaot.md
+++ b/docs/workflow/building/coreclr/nativeaot.md
@@ -109,6 +109,10 @@ Build library tests by passing the `libs.tests` subset together with the `/p:Tes
* [ILC Compiler Architecture](/docs/design/coreclr/botr/ilc-architecture.md)
* [Managed Type System](/docs/design/coreclr/botr/managed-type-system.md)
+## Native Sanitizers
+
+Using native sanitizers with NativeAOT requires additional care compared to using them with CoreCLR. In addition to passing the `-fsanitize` flag to the command that builds NativeAOT, you must also pass the `EnableNativeSanitizers` MSBuild property to any commands that build projects with a sanitized NativeAOT build to ensure that any sanitizer runtimes are correctly linked with the project.
+
## Further Reading
If you want to know more about working with _NativeAOT_ in general, you can check out their [more in-depth docs](/src/coreclr/nativeaot/docs/README.md) in the `src/coreclr/nativeaot` subtree.
diff --git a/docs/workflow/building/coreclr/windows-instructions.md b/docs/workflow/building/coreclr/windows-instructions.md
index 38ca5af6f513d6..3ab6b33bc04747 100644
--- a/docs/workflow/building/coreclr/windows-instructions.md
+++ b/docs/workflow/building/coreclr/windows-instructions.md
@@ -45,3 +45,23 @@ build.cmd -s clr -c Release -arch arm64 -msbuild
```
Since this is still in an experimental phase, the recommended way for building ARM64 is cross-compiling from an x64 machine. Instructions on how to do this can be found at the [cross-building doc](/docs/workflow/building/coreclr/cross-building.md#cross-compiling-for-arm32-and-arm64).
+
+## Native Sanitizers
+
+CoreCLR can be built with native sanitizers like AddressSanitizer to help catch memory safety issues. To build the project with native sanitizers, add the `-fsanitize address` argument to the build script like the following:
+
+```cmd
+build.cmd -s clr -fsanitize address
+```
+
+When building the repo with any native sanitizers, you should build all native components in the repo with the same set of sanitizers.
+
+The following sanitizers are supported for CoreCLR on Windows:
+
+| Sanitizer Name | Minimum VS Version | `-fsanitize` argument | Support Status |
+|----------------|--------------------|-----------------------|----------------|
+| AddressSanitizer | not yet released | `address` | experimental |
+
+## Using a custom compiler environment
+
+If you ever need to use a custom compiler environment for the native builds on Windows, you can set the `SkipVCEnvInit` environment variable to `1`. The build system will skip discovering Visual Studio and initializing its development environment when this flag is used. This is only required for very advanced scenarios and should be used rarely.
diff --git a/docs/workflow/building/libraries/README.md b/docs/workflow/building/libraries/README.md
index f24d47e608271e..f1e0726e69074b 100644
--- a/docs/workflow/building/libraries/README.md
+++ b/docs/workflow/building/libraries/README.md
@@ -105,6 +105,16 @@ By default the `build` script only builds the product libraries and none of the
For Windows, replace `./build.sh` with `build.cmd`.
+### Building the native components with native sanitizers
+
+The libraries native components can be built with native sanitizers like AddressSanitizer to help catch memory safety issues. To build the project with native sanitizers, add the `-fsanitize` argument to the build script like the following:
+
+```bash
+build.sh -s libs -fsanitize address
+```
+
+When building the repo with any native sanitizers, you should build all native components in the repo with the same set of sanitizers.
+
### How to build native components only
The libraries build contains some native code. This includes shims over libc, openssl, gssapi, and zlib. The build system uses CMake to generate Makefiles using clang. The build also uses git for generating some version information.
diff --git a/eng/Subsets.props b/eng/Subsets.props
index 6bd09ac2261a5b..4f98634f6372e1 100644
--- a/eng/Subsets.props
+++ b/eng/Subsets.props
@@ -253,8 +253,11 @@
Category="clr" />
-
-
+
+
+
+
+
+
+
@@ -317,8 +338,8 @@
-
-
+
+
diff --git a/eng/build.ps1 b/eng/build.ps1
index fc2712fcafe512..67440febafd5ce 100644
--- a/eng/build.ps1
+++ b/eng/build.ps1
@@ -22,6 +22,7 @@ Param(
[switch]$msbuild,
[string]$cmakeargs,
[switch]$pgoinstrument,
+ [string[]]$fsanitize,
[Parameter(ValueFromRemainingArguments=$true)][String[]]$properties
)
@@ -84,10 +85,13 @@ function Get-Help() {
Write-Host ""
Write-Host "Native build settings:"
- Write-Host " -cmakeargs User-settable additional arguments passed to CMake."
- Write-Host " -ninja Use Ninja to drive the native build. (default)"
- Write-Host " -msbuild Use MSBuild to drive the native build. This is a no-op for Mono."
- Write-Host " -pgoinstrument Build the CLR with PGO instrumentation."
+ Write-Host " -cmakeargs User-settable additional arguments passed to CMake."
+ Write-Host " -ninja Use Ninja to drive the native build. (default)"
+ Write-Host " -msbuild Use MSBuild to drive the native build. This is a no-op for Mono."
+ Write-Host " -pgoinstrument Build the CLR with PGO instrumentation."
+ Write-Host " -fsanitize (address) Build the native components with the specified sanitizers."
+ Write-Host " Sanitizers can be specified with a comma-separated list."
+ Write-Host ""
Write-Host "Command-line arguments not listed above are passed through to MSBuild."
Write-Host "The above arguments can be shortened as much as to be unambiguous."
@@ -220,7 +224,7 @@ if ($vs) {
# Put our local dotnet.exe on PATH first so Visual Studio knows which one to use
$env:PATH=($env:DOTNET_ROOT + ";" + $env:PATH);
-
+
# Disable .NET runtime signature validation errors which errors for local builds
$env:VSDebugger_ValidateDotnetDebugLibSignatures=0;
@@ -269,6 +273,7 @@ foreach ($argument in $PSBoundParameters.Keys)
# configuration and arch can be specified multiple times, so they should be no-ops here
"configuration" {}
"arch" {}
+ "fsanitize" { $arguments += " /p:EnableNativeSanitizers=$($PSBoundParameters[$argument])"}
default { $arguments += " /p:$argument=$($PSBoundParameters[$argument])" }
}
}
diff --git a/eng/build.sh b/eng/build.sh
index c4f18b3051df29..772d7ac8be82cb 100755
--- a/eng/build.sh
+++ b/eng/build.sh
@@ -84,6 +84,7 @@ usage()
echo " --keepnativesymbols Optional argument: set to true to keep native symbols/debuginfo in generated binaries."
echo " --ninja Optional argument: set to true to use Ninja instead of Make to run the native build."
echo " --pgoinstrument Optional argument: build PGO-instrumented runtime"
+ echo " --fsanitize Optional argument: Specify native sanitizers to instrument the native build with. Supported values are: 'address'."
echo ""
echo "Command line arguments starting with '/p:' are passed through to MSBuild."
@@ -509,6 +510,21 @@ while [[ $# > 0 ]]; do
shift 1
;;
+ -fsanitize)
+ if [ -z ${2+x} ]; then
+ echo "No value for -fsanitize is supplied. See help (--help) for supported values." 1>&2
+ exit 1
+ fi
+ arguments="$arguments /p:EnableNativeSanitizers=$2"
+ shift 2
+ ;;
+
+ -fsanitize=*)
+ sanitizers="${opt/#-fsanitize=/}" # -fsanitize=address => address
+ arguments="$arguments /p:EnableNativeSanitizers=$sanitizers"
+ shift 2
+ ;;
+
*)
extraargs="$extraargs $1"
shift 1
diff --git a/eng/liveBuilds.targets b/eng/liveBuilds.targets
index 3830816fc037a2..efdf7a9c865a2c 100644
--- a/eng/liveBuilds.targets
+++ b/eng/liveBuilds.targets
@@ -25,7 +25,7 @@
$([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', 'sharedFramework'))
$([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', 'crossgen2'))
$([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', 'ilc-published'))
- $([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', '$(BuildArchitecture)', 'ilc'))
+ $([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', '$(BuildArchitecture)', 'ilc'))
$([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', 'aotsdk'))
$([MSBuild]::NormalizeDirectory('$(CoreCLRArtifactsPath)', 'build'))
diff --git a/eng/native/build-commons.sh b/eng/native/build-commons.sh
index 410aab20b0a02f..d9eb04cd8aaabd 100755
--- a/eng/native/build-commons.sh
+++ b/eng/native/build-commons.sh
@@ -270,6 +270,7 @@ usage()
echo "-portablebuild: pass -portablebuild=false to force a non-portable build."
echo "-skipconfigure: skip build configuration."
echo "-keepnativesymbols: keep native/unmanaged debug symbols."
+ echo "-fsanitize: Enable native sanitizers"
echo "-verbose: optional argument to enable verbose build output."
echo ""
echo "Additional Options:"
@@ -392,6 +393,17 @@ while :; do
__CMakeArgs="$__CMakeArgs -DCLR_CMAKE_KEEP_NATIVE_SYMBOLS=true"
;;
+ -fsanitize)
+ __CMakeArgs="$__CMakeArgs -DCLR_CMAKE_ENABLE_SANITIZERS=$2"
+ EnableNativeSanitizers=$2
+ shift
+ ;;
+ -fsanitize=*)
+ sanitizers="${lowerI/#-fsanitize=/}" # -fsanitize=address => address
+ __CMakeArgs="$__CMakeArgs -DCLR_CMAKE_ENABLE_SANITIZERS=$sanitizers"
+ EnableNativeSanitizers=$sanitizers
+ ;;
+
ninja|-ninja)
__UseNinja=1
;;
diff --git a/eng/native/configurecompiler.cmake b/eng/native/configurecompiler.cmake
index ee8e324db96f8b..bb734c59d55572 100644
--- a/eng/native/configurecompiler.cmake
+++ b/eng/native/configurecompiler.cmake
@@ -1,3 +1,7 @@
+# Due to how we build the libraries native build as part of the CoreCLR build as well as standalone,
+# we can end up coming to this file twice. Only run it once to simplify our build.
+include_guard()
+
include(${CMAKE_CURRENT_LIST_DIR}/configuretools.cmake)
# Set initial flags for each configuration
@@ -78,7 +82,15 @@ if (MSVC)
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /DEBUG")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /DEBUGTYPE:CV,FIXUP")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /PDBCOMPRESS")
- set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /STACK:1572864")
+ # For sanitized builds, we bump up the stack size to 8MB to match behavior on Unix platforms.
+ # Sanitized builds can use significantly more stack space than non-sanitized builds due to instrumentation.
+ # We don't want to change the default stack size for all builds, as that will likely cause confusion and will
+ # increase memory usage.
+ if (CLR_CMAKE_ENABLE_SANITIZERS)
+ set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /STACK:0x800000")
+ else()
+ set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /STACK:0x180000")
+ endif()
if(EXISTS ${CLR_SOURCELINK_FILE_PATH})
set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} /sourcelink:${CLR_SOURCELINK_FILE_PATH}")
@@ -112,10 +124,6 @@ if (MSVC)
add_linker_flag(/OPT:ICF RELWITHDEBINFO)
set(CMAKE_STATIC_LINKER_FLAGS_RELWITHDEBINFO "${CMAKE_STATIC_LINKER_FLAGS_RELWITHDEBINFO} /LTCG")
- # Force uCRT to be dynamically linked for Release build
- add_linker_flag(/NODEFAULTLIB:libucrt.lib RELEASE)
- add_linker_flag(/DEFAULTLIB:ucrt.lib RELEASE)
-
elseif (CLR_CMAKE_HOST_UNIX)
# Set the values to display when interactively configuring CMAKE_BUILD_TYPE
set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS "DEBUG;CHECKED;RELEASE;RELWITHDEBINFO")
@@ -123,62 +131,6 @@ elseif (CLR_CMAKE_HOST_UNIX)
# Use uppercase CMAKE_BUILD_TYPE for the string comparisons below
string(TOUPPER ${CMAKE_BUILD_TYPE} UPPERCASE_CMAKE_BUILD_TYPE)
- set(CLR_SANITIZE_CXX_OPTIONS "")
- set(CLR_SANITIZE_LINK_OPTIONS "")
-
- # set the CLANG sanitizer flags for debug build
- if(UPPERCASE_CMAKE_BUILD_TYPE STREQUAL DEBUG OR UPPERCASE_CMAKE_BUILD_TYPE STREQUAL CHECKED)
- # obtain settings from running enablesanitizers.sh
- string(FIND "$ENV{DEBUG_SANITIZERS}" "asan" __ASAN_POS)
- string(FIND "$ENV{DEBUG_SANITIZERS}" "ubsan" __UBSAN_POS)
- if ((${__ASAN_POS} GREATER -1) OR (${__UBSAN_POS} GREATER -1))
- list(APPEND CLR_SANITIZE_CXX_OPTIONS -fsanitize-blacklist=${CMAKE_CURRENT_SOURCE_DIR}/sanitizerblacklist.txt)
- set (CLR_CXX_SANITIZERS "")
- set (CLR_LINK_SANITIZERS "")
- if (${__ASAN_POS} GREATER -1)
- list(APPEND CLR_CXX_SANITIZERS address)
- list(APPEND CLR_LINK_SANITIZERS address)
- set(CLR_SANITIZE_CXX_FLAGS "${CLR_SANITIZE_CXX_FLAGS}address,")
- set(CLR_SANITIZE_LINK_FLAGS "${CLR_SANITIZE_LINK_FLAGS}address,")
- add_definitions(-DHAS_ASAN)
- message("Address Sanitizer (asan) enabled")
- endif ()
- if (${__UBSAN_POS} GREATER -1)
- # all sanitizer flags are enabled except alignment (due to heavy use of __unaligned modifier)
- list(APPEND CLR_CXX_SANITIZERS
- "bool"
- bounds
- enum
- float-cast-overflow
- float-divide-by-zero
- "function"
- integer
- nonnull-attribute
- null
- object-size
- "return"
- returns-nonnull-attribute
- shift
- unreachable
- vla-bound
- vptr)
- list(APPEND CLR_LINK_SANITIZERS
- undefined)
- message("Undefined Behavior Sanitizer (ubsan) enabled")
- endif ()
- list(JOIN CLR_CXX_SANITIZERS "," CLR_CXX_SANITIZERS_OPTIONS)
- list(APPEND CLR_SANITIZE_CXX_OPTIONS "-fsanitize=${CLR_CXX_SANITIZERS_OPTIONS}")
- list(JOIN CLR_LINK_SANITIZERS "," CLR_LINK_SANITIZERS_OPTIONS)
- list(APPEND CLR_SANITIZE_LINK_OPTIONS "-fsanitize=${CLR_LINK_SANITIZERS_OPTIONS}")
-
- # -O1: optimization level used instead of -O0 to avoid compile error "invalid operand for inline asm constraint"
- add_compile_options("$<$,$>:${CLR_SANITIZE_CXX_OPTIONS};-fdata-sections;-O1>")
- add_linker_flag("${CLR_SANITIZE_LINK_OPTIONS}" DEBUG CHECKED)
- # -Wl and --gc-sections: drop unused sections\functions (similar to Windows /Gy function-level-linking)
- add_linker_flag("-Wl,--gc-sections" DEBUG CHECKED)
- endif ()
- endif(UPPERCASE_CMAKE_BUILD_TYPE STREQUAL DEBUG OR UPPERCASE_CMAKE_BUILD_TYPE STREQUAL CHECKED)
-
if(CLR_CMAKE_HOST_BROWSER OR CLR_CMAKE_HOST_WASI)
# The emscripten build has additional warnings so -Werror breaks
add_compile_options(-Wno-unused-parameter)
@@ -187,6 +139,129 @@ elseif (CLR_CMAKE_HOST_UNIX)
endif()
endif(MSVC)
+if (CLR_CMAKE_ENABLE_SANITIZERS)
+ set (CLR_CMAKE_BUILD_SANITIZERS "")
+ set (CLR_CMAKE_SANITIZER_RUNTIMES "")
+ string(FIND "${CLR_CMAKE_ENABLE_SANITIZERS}" "address" __ASAN_POS)
+ if(${__ASAN_POS} GREATER -1)
+ # Set up build flags for AddressSanitizer
+ set (CLR_CMAKE_ENABLE_ASAN ON)
+ if (MSVC)
+ # /RTC1 is added by default by CMake and incompatible with ASAN, so remove it.
+ string(REPLACE "/RTC1" "" CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG}")
+ string(REPLACE "/RTC1" "" CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG}")
+ string(REPLACE "/RTC1" "" CMAKE_SHARED_LINKER_FLAGS_DEBUG "${CMAKE_SHARED_LINKER_FLAGS_DEBUG}")
+ string(REPLACE "/RTC1" "" CMAKE_EXE_LINKER_FLAGS_DEBUG "${CMAKE_EXE_LINKER_FLAGS_DEBUG}")
+ endif()
+ # For Mac and Windows platforms, we install the ASAN runtime next to the rest of our outputs to ensure that it's present when we execute our tests on Helix machines
+ # The rest of our platforms use statically-linked ASAN so this isn't a concern for those platforms.
+ if (CLR_CMAKE_TARGET_OSX OR CLR_CMAKE_TARGET_MACCATALYST)
+ function(getSanitizerRuntimeDirectory output)
+ enable_language(C)
+ execute_process(
+ COMMAND ${CMAKE_C_COMPILER} -print-resource-dir
+ OUTPUT_VARIABLE compilerResourceDir
+ OUTPUT_STRIP_TRAILING_WHITESPACE)
+ set(${output} "${compilerResourceDir}/lib/darwin/" PARENT_SCOPE)
+ endfunction()
+ getSanitizerRuntimeDirectory(sanitizerRuntimeDirectory)
+ find_library(ASAN_RUNTIME clang_rt.asan_osx_dynamic PATHS ${sanitizerRuntimeDirectory})
+ add_compile_definitions(SANITIZER_SHARED_RUNTIME)
+ elseif (CLR_CMAKE_TARGET_WIN32)
+ function(getSanitizerRuntimeDirectory output archSuffixOutput)
+ get_filename_component(compiler_directory "${CMAKE_C_COMPILER}" DIRECTORY)
+ set(${output} "${compiler_directory}" PARENT_SCOPE)
+ if (CLR_CMAKE_TARGET_ARCH_I386)
+ set(${archSuffixOutput} "i386" PARENT_SCOPE)
+ elseif (CLR_CMAKE_TARGET_ARCH_AMD64)
+ set(${archSuffixOutput} "x86_64" PARENT_SCOPE)
+ elseif (CLR_CMAKE_TARGET_ARCH_ARM)
+ set(${archSuffixOutput} "armhf" PARENT_SCOPE)
+ elseif (CLR_CMAKE_TARGET_ARCH_ARM64)
+ set(${archSuffixOutput} "aarch64" PARENT_SCOPE)
+ endif()
+ endfunction()
+ getSanitizerRuntimeDirectory(sanitizerRuntimeDirectory archSuffix)
+ set(ASAN_RUNTIME "${sanitizerRuntimeDirectory}/clang_rt.asan_dynamic-${archSuffix}.dll")
+ add_compile_definitions(SANITIZER_SHARED_RUNTIME)
+ endif()
+ if (CLR_CMAKE_ENABLE_ASAN)
+ message("-- Address Sanitizer (asan) enabled")
+ list(APPEND CLR_CMAKE_BUILD_SANITIZERS
+ address)
+ list(APPEND CLR_CMAKE_SANITIZER_RUNTIMES
+ address)
+ # We can't use preprocessor defines to determine if we're building with ASAN in assembly, so we'll
+ # define the preprocessor define ourselves.
+ add_compile_definitions($<$:HAS_ADDRESS_SANITIZER>)
+
+ # Disable the use-after-return check for ASAN on Clang. This is because we have a lot of code that
+ # depends on the fact that our locals are not saved in a parallel stack, so we can't enable this today.
+ # If we ever have a way to detect a parallel stack and track its bounds, we can re-enable this check.
+ add_compile_options($<$:-fsanitize-address-use-after-return=never>)
+ add_compile_options($<$:-fsanitize-address-use-after-return=never>)
+ endif()
+ endif()
+
+ # Set up build flags for UBSanitizer
+ if (CLR_CMAKE_HOST_UNIX)
+
+ set (CLR_CMAKE_ENABLE_UBSAN OFF)
+ # COMPAT: Allow enabling UBSAN in Debug/Checked builds via an environment variable.
+ if(UPPERCASE_CMAKE_BUILD_TYPE STREQUAL DEBUG OR UPPERCASE_CMAKE_BUILD_TYPE STREQUAL CHECKED)
+ # obtain settings from running enablesanitizers.sh
+ string(FIND "$ENV{DEBUG_SANITIZERS}" "ubsan" __UBSAN_ENV_POS)
+ if (${__UBSAN_ENV_POS} GREATER -1)
+ set(CLR_CMAKE_ENABLE_UBSAN ON)
+ endif()
+ endif()
+ string(FIND "${CLR_CMAKE_ENABLE_SANITIZERS}" "undefined" __UBSAN_POS)
+ if (${__UBSAN_POS} GREATER -1)
+ set(CLR_CMAKE_ENABLE_UBSAN ON)
+ endif()
+
+ # set the CLANG sanitizer flags for debug build
+ if(CLR_CMAKE_ENABLE_UBSAN)
+ list(APPEND CLR_CMAKE_BUILD_SANITIZE_OPTIONS -fsanitize-blacklist=${CMAKE_CURRENT_SOURCE_DIR}/sanitizerblacklist.txt)
+ # all sanitizer flags are enabled except alignment (due to heavy use of __unaligned modifier)
+ list(APPEND CLR_CMAKE_BUILD_SANITIZERS
+ "bool"
+ bounds
+ enum
+ float-cast-overflow
+ float-divide-by-zero
+ "function"
+ integer
+ nonnull-attribute
+ null
+ object-size
+ "return"
+ returns-nonnull-attribute
+ shift
+ unreachable
+ vla-bound
+ vptr)
+ list(APPEND CLR_CMAKE_SANITIZER_RUNTIMES
+ undefined)
+ message("-- Undefined Behavior Sanitizer (ubsan) enabled")
+ endif ()
+ endif()
+ list(JOIN CLR_CMAKE_BUILD_SANITIZERS "," CLR_CMAKE_BUILD_SANITIZERS)
+ list(JOIN CLR_CMAKE_SANITIZER_RUNTIMES "," CLR_LINK_SANITIZERS_OPTIONS)
+ if (CLR_CMAKE_BUILD_SANITIZERS)
+ list(APPEND CLR_CMAKE_BUILD_SANITIZE_OPTIONS "-fsanitize=${CLR_CMAKE_BUILD_SANITIZERS}")
+ endif()
+ if (CLR_CMAKE_SANITIZER_RUNTIMES)
+ list(APPEND CLR_CMAKE_LINK_SANITIZE_OPTIONS "-fsanitize=${CLR_CMAKE_SANITIZER_RUNTIMES}")
+ endif()
+ if (MSVC)
+ add_compile_options("$<$:${CLR_CMAKE_BUILD_SANITIZE_OPTIONS}>")
+ else()
+ add_compile_options("$<$:${CLR_CMAKE_BUILD_SANITIZE_OPTIONS}>")
+ add_linker_flag("${CLR_CMAKE_LINK_SANITIZE_OPTIONS}")
+ endif()
+endif()
+
# CLR_ADDITIONAL_LINKER_FLAGS - used for passing additional arguments to linker
# CLR_ADDITIONAL_COMPILER_OPTIONS - used for passing additional arguments to compiler
#
@@ -511,7 +586,7 @@ if (CLR_CMAKE_HOST_UNIX)
add_compile_options($<$:-Wno-misleading-indentation>)
add_compile_options($<$:-Wno-stringop-overflow>)
add_compile_options($<$:-Wno-restrict>)
- add_compile_options($<$:-Wno-stringop-truncation>)
+ add_compile_options($<$:-Wno-stringop-truncation>)
if (CMAKE_CXX_COMPILER_VERSION VERSION_LESS 12.0)
# this warning is only reported by g++ 11 in debug mode when building
@@ -785,6 +860,15 @@ if (MSVC)
# production-time scenarios.
set(CMAKE_MSVC_RUNTIME_LIBRARY MultiThreaded$<$,$>,$>>>:Debug>)
+ if (NOT CLR_CMAKE_ENABLE_SANITIZERS)
+ # Force uCRT to be dynamically linked for Release build
+ # We won't do this for sanitized builds as the dynamic CRT is not compatible with the static sanitizer runtime and
+ # the dynamic sanitizer runtime is not redistributable. Sanitized runtime builds are not production-time scenarios
+ # so we don't get the benefits of a dynamic CRT for sanitized runtime builds.
+ add_linker_flag(/NODEFAULTLIB:libucrt.lib RELEASE)
+ add_linker_flag(/DEFAULTLIB:ucrt.lib RELEASE)
+ endif()
+
add_compile_options($<$:/ZH:SHA_256>)
if (CLR_CMAKE_TARGET_ARCH_ARM OR CLR_CMAKE_TARGET_ARCH_ARM64)
@@ -796,6 +880,15 @@ if (MSVC)
add_compile_options($<$:/nologo>)
endif (MSVC)
+# Configure non-MSVC compiler flags that apply to all platforms (unix-like or otherwise)
+if (NOT MSVC)
+ # Check for sometimes suppressed warnings
+ check_c_compiler_flag(-Wreserved-identifier COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ if(COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ add_compile_definitions(COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ endif()
+endif()
+
if(CLR_CMAKE_ENABLE_CODE_COVERAGE)
if(CLR_CMAKE_HOST_UNIX)
diff --git a/eng/native/functions.cmake b/eng/native/functions.cmake
index 5b8e47c0a43c4b..d5ef9ed625996a 100644
--- a/eng/native/functions.cmake
+++ b/eng/native/functions.cmake
@@ -89,9 +89,11 @@ function(get_compile_definitions DefinitionName)
set(LastGeneratorExpression "")
foreach(DEFINITION IN LISTS COMPILE_DEFINITIONS_LIST)
# If there is a definition that uses the $ generator expression
+ # or the $ generator expression,
# we need to remove it since that generator expression is only valid on binary targets.
# Assume that the value is 0.
string(REGEX REPLACE "\\$]+>" "0" DEFINITION "${DEFINITION}")
+ string(REGEX REPLACE "\\$]+(,[^>]+)*>" "0" DEFINITION "${DEFINITION}")
if (${DEFINITION} MATCHES "^\\$<(.+):([^>]+)(>?)$")
if("${CMAKE_MATCH_3}" STREQUAL "")
@@ -631,25 +633,34 @@ function(link_natvis_sources_for_target targetName linkKind)
endforeach()
endfunction()
+# Add sanitizer runtime support code to the target.
+function(add_sanitizer_runtime_support targetName)
+ # Add sanitizer support functions.
+ if (CLR_CMAKE_ENABLE_ASAN)
+ target_sources(${targetName} PRIVATE "$<$,EXECUTABLE>:${CLR_SRC_NATIVE_DIR}/minipal/asansupport.cpp>")
+ endif()
+endfunction()
+
function(add_executable_clr targetName)
- if(NOT WIN32)
- add_executable(${ARGV} ${VERSION_FILE_PATH})
- disable_pax_mprotect(${ARGV})
- else()
- add_executable(${ARGV})
- endif(NOT WIN32)
- if(NOT CLR_CMAKE_KEEP_NATIVE_SYMBOLS)
- strip_symbols(${ARGV0} symbolFile)
- endif()
+ if(NOT WIN32)
+ add_executable(${ARGV} ${VERSION_FILE_PATH})
+ disable_pax_mprotect(${ARGV})
+ else()
+ add_executable(${ARGV})
+ endif(NOT WIN32)
+ add_sanitizer_runtime_support(${targetName})
+ if(NOT CLR_CMAKE_KEEP_NATIVE_SYMBOLS)
+ strip_symbols(${ARGV0} symbolFile)
+ endif()
endfunction()
function(add_library_clr targetName kind)
- if(NOT WIN32 AND "${kind}" STREQUAL "SHARED")
- add_library(${ARGV} ${VERSION_FILE_PATH})
- else()
- add_library(${ARGV})
- endif()
- if("${kind}" STREQUAL "SHARED" AND NOT CLR_CMAKE_KEEP_NATIVE_SYMBOLS)
- strip_symbols(${ARGV0} symbolFile)
- endif()
+ if(NOT WIN32 AND "${kind}" STREQUAL "SHARED")
+ add_library(${ARGV} ${VERSION_FILE_PATH})
+ else()
+ add_library(${ARGV})
+ endif()
+ if("${kind}" STREQUAL "SHARED" AND NOT CLR_CMAKE_KEEP_NATIVE_SYMBOLS)
+ strip_symbols(${ARGV0} symbolFile)
+ endif()
endfunction()
diff --git a/eng/native/ijw/IJW.cmake b/eng/native/ijw/IJW.cmake
index 4222b9b15b9de2..9ef90525dda8ba 100644
--- a/eng/native/ijw/IJW.cmake
+++ b/eng/native/ijw/IJW.cmake
@@ -1,8 +1,7 @@
if (CLR_CMAKE_HOST_WIN32)
function(remove_ijw_incompatible_options options updatedOptions)
-
- # IJW isn't compatible with Ehsc, which CMake enables by default,
+ # IJW isn't compatible with Ehsc, which CMake enables by default
if(options MATCHES "/EHsc")
string(REPLACE "/EHsc" "" options "${options}")
endif()
@@ -22,6 +21,12 @@ if (CLR_CMAKE_HOST_WIN32)
string(REPLACE "/GR-" "" options "${options}")
endif()
+ # Disable native sanitizers for IJW since we don't want to have to locate
+ # and copy the sanitizer runtimes and IJW must be built with a dynamic CRT.
+ if (options MATCHES "-fsanitize=")
+ string(REGEX REPLACE "-fsanitize=[a-zA-z,]+" "" options "${options}")
+ endif()
+
SET(${updatedOptions} "${options}" PARENT_SCOPE)
endfunction()
@@ -61,6 +66,10 @@ if (CLR_CMAKE_HOST_WIN32)
remove_ijw_incompatible_options("${CMAKE_CXX_FLAGS}" CMAKE_CXX_FLAGS)
+ get_directory_property(dirCompileOptions COMPILE_OPTIONS)
+ remove_ijw_incompatible_options("${dirCompileOptions}" dirCompileOptions)
+ set_directory_properties(PROPERTIES COMPILE_OPTIONS "${dirCompileOptions}")
+
set(CLR_SDK_REF_PACK_OUTPUT "")
set(CLR_SDK_REF_PACK_DISCOVERY_ERROR "")
set(CLR_SDK_REF_PACK_DISCOVERY_RESULT 0)
diff --git a/eng/native/init-vs-env.cmd b/eng/native/init-vs-env.cmd
index 6c1ad8f3a17862..273f49b3392c2d 100644
--- a/eng/native/init-vs-env.cmd
+++ b/eng/native/init-vs-env.cmd
@@ -61,9 +61,13 @@ exit /b 1
if "%__VCBuildArch%"=="" exit /b 0
:: Set the environment for the native build
-if not exist "%VCINSTALLDIR%Auxiliary\Build\vcvarsall.bat" goto :VSMissing
-call "%VCINSTALLDIR%Auxiliary\Build\vcvarsall.bat" %__VCBuildArch%
-if not "%ErrorLevel%"=="0" exit /b 1
+:: We can set SkipVCEnvInit to skip setting up the MSVC environment from VS and instead assume that the current environment is set up correctly.
+:: This is very useful for testing with new MSVC versions that aren't in a VS build yet.
+if not defined SkipVCEnvInit (
+ if not exist "%VCINSTALLDIR%Auxiliary\Build\vcvarsall.bat" goto :VSMissing
+ call "%VCINSTALLDIR%Auxiliary\Build\vcvarsall.bat" %__VCBuildArch%
+ if not "%ErrorLevel%"=="0" exit /b 1
+)
set "__VCBuildArch="
diff --git a/eng/nativeSanitizers.targets b/eng/nativeSanitizers.targets
new file mode 100644
index 00000000000000..69ec76b93487c6
--- /dev/null
+++ b/eng/nativeSanitizers.targets
@@ -0,0 +1,24 @@
+
+
+
+ x86_64
+
+
+ i386
+
+
+ armhf
+
+
+ arm64
+
+
+
+
+
+
+
+
+
+
+
diff --git a/eng/pipelines/common/global-build-job.yml b/eng/pipelines/common/global-build-job.yml
index 3ac90ee3387b40..e6a07c9b4c6033 100644
--- a/eng/pipelines/common/global-build-job.yml
+++ b/eng/pipelines/common/global-build-job.yml
@@ -115,6 +115,10 @@ jobs:
- name: _monoAotCrossCompileArg
value: 'cross'
+ # Set no native sanitizers by default
+ - name: _nativeSanitizersArg
+ value: ''
+
- ${{ each variableTemplate in parameters.extraVariablesTemplates }}:
- template: ${{ variableTemplate.template }}
parameters:
@@ -138,7 +142,6 @@ jobs:
- ${{ each variable in parameters.variables }}:
- ${{ variable }}
-
steps:
- checkout: self
clean: true
diff --git a/eng/pipelines/common/templates/runtimes/build-runtime-tests-and-send-to-helix.yml b/eng/pipelines/common/templates/runtimes/build-runtime-tests-and-send-to-helix.yml
index 3da6cc22300cd7..396fd6e87c3249 100644
--- a/eng/pipelines/common/templates/runtimes/build-runtime-tests-and-send-to-helix.yml
+++ b/eng/pipelines/common/templates/runtimes/build-runtime-tests-and-send-to-helix.yml
@@ -6,7 +6,6 @@ parameters:
testBuildArgs: ''
crossBuild: false
readyToRun: false
- liveLibrariesBuildConfig: ''
compositeBuildMode: false
helixQueues: ''
displayNameArgs: ''
@@ -36,7 +35,6 @@ steps:
osSubgroup: ${{ parameters.osSubgroup }}
archType: ${{ parameters.archType }}
buildConfig: ${{ parameters.buildConfig }}
- liveLibrariesBuildConfig: ${{ parameters.liveLibrariesBuildConfig }}
testBuildArgs: ${{ parameters.testBuildArgs }}
# Build a Mono LLVM AOT cross-compiler for non-amd64 targets (in this case, just arm64)
diff --git a/eng/pipelines/common/templates/runtimes/build-runtime-tests.yml b/eng/pipelines/common/templates/runtimes/build-runtime-tests.yml
index bba48b87c9ab60..f9ef84a49c164a 100644
--- a/eng/pipelines/common/templates/runtimes/build-runtime-tests.yml
+++ b/eng/pipelines/common/templates/runtimes/build-runtime-tests.yml
@@ -3,7 +3,6 @@ parameters:
osSubgroup: ''
archType: ''
buildConfig: ''
- liveLibrariesBuildConfig: ''
testBuildArgs: ''
#arcade-specific parameters
condition: always()
@@ -17,8 +16,8 @@ parameters:
steps:
- ${{ if eq(parameters.osGroup, 'windows') }}:
- - script: $(Build.SourcesDirectory)/src/tests/build$(scriptExt) $(crossArg) ci ${{ parameters.archType }} $(buildConfigUpper) $(priorityArg) $(runtimeFlavorArgs) ${{ parameters.testBuildArgs }} $(runtimeVariantArg) /p:LibrariesConfiguration=${{ coalesce(parameters.liveLibrariesBuildConfig, parameters.buildConfig) }}
+ - script: $(Build.SourcesDirectory)/src/tests/build$(scriptExt) $(crossArg) ci ${{ parameters.archType }} $(buildConfigUpper) $(_nativeSanitizersArg) $(priorityArg) $(runtimeFlavorArgs) ${{ parameters.testBuildArgs }} $(runtimeVariantArg) $(librariesConfigurationArg)
displayName: Build Tests
- ${{ if ne(parameters.osGroup, 'windows') }}:
- - script: $(Build.SourcesDirectory)/src/tests/build$(scriptExt) $(crossArg) ci os ${{ parameters.osGroup }} ${{ parameters.archType }} $(buildConfigUpper) $(priorityArg) $(runtimeFlavorArgs) ${{ parameters.testBuildArgs }} $(runtimeVariantArg) /p:LibrariesConfiguration=${{ coalesce(parameters.liveLibrariesBuildConfig, parameters.buildConfig) }}
+ - script: $(Build.SourcesDirectory)/src/tests/build$(scriptExt) $(crossArg) ci os ${{ parameters.osGroup }} ${{ parameters.archType }} $(buildConfigUpper) $(_nativeSanitizersArg) $(priorityArg) $(runtimeFlavorArgs) ${{ parameters.testBuildArgs }} $(runtimeVariantArg) $(librariesConfigurationArg)
displayName: Build Tests
diff --git a/eng/pipelines/common/templates/runtimes/test-variables.yml b/eng/pipelines/common/templates/runtimes/test-variables.yml
index d3eb48f309df73..285f13caeb0821 100644
--- a/eng/pipelines/common/templates/runtimes/test-variables.yml
+++ b/eng/pipelines/common/templates/runtimes/test-variables.yml
@@ -1,8 +1,10 @@
parameters:
testGroup: 'innerloop'
readyToRun: false
+ sanitizers: ''
runtimeFlavor: ''
runtimeVariant: ''
+ liveLibrariesBuildConfig: ''
variables:
@@ -28,6 +30,15 @@ variables:
- ${{ if in(parameters.testGroup, 'outerloop') }}:
- name: timeoutPerTestCollectionInMinutes
value: 120
+ # AddressSanitizer can have up to a 2x slowdown
+ - ${{ if eq(parameters.sanitizers, 'address') }}:
+ - name: timeoutPerTestInMinutes
+ value: 20
+ - name: timeoutPerTestCollectionInMinutes
+ value: 60
+ - ${{ if in(parameters.testGroup, 'outerloop') }}:
+ - name: timeoutPerTestCollectionInMinutes
+ value: 240
- ${{ if eq(parameters.readyToRun, true) }}:
- name: timeoutPerTestCollectionInMinutes
value: 90
@@ -102,3 +113,10 @@ variables:
- ${{ if eq(parameters.osGroup, 'windows') }}:
- name: priorityArg
value: '-priority=1'
+
+ - name: librariesConfigurationArg
+ value: '/p:LibrariesConfiguration=$(buildConfigUpper)'
+
+ - ${{ if ne(parameters.liveLibrariesBuildConfig, '') }}:
+ - name: librariesConfigurationArg
+ value: '/p:LibrariesConfiguration=${{ parameters.liveLibrariesBuildConfig }}'
diff --git a/eng/pipelines/coreclr/nativeaot-post-build-steps.yml b/eng/pipelines/coreclr/nativeaot-post-build-steps.yml
index c3d65b8281fd17..94761028f48ab0 100644
--- a/eng/pipelines/coreclr/nativeaot-post-build-steps.yml
+++ b/eng/pipelines/coreclr/nativeaot-post-build-steps.yml
@@ -27,5 +27,5 @@ steps:
# Publishing tooling doesn't support different configs between runtime and libs, so only run tests in Release config
- ${{ if eq(parameters.buildConfig, 'release') }}:
- - script: $(Build.SourcesDirectory)$(dir)build$(scriptExt) -ci -arch ${{ parameters.archType }} $(_osParameter) -s libs.tests -c $(_BuildConfig) $(crossArg) /p:TestAssemblies=false /p:RunNativeAotTestApps=true $(_officialBuildParameter) /bl:$(Build.SourcesDirectory)/artifacts/log/$(buildConfigUpper)/NativeAotTests.binlog ${{ parameters.extraTestArgs }}
+ - script: $(Build.SourcesDirectory)$(dir)build$(scriptExt) -ci -arch ${{ parameters.archType }} $(_osParameter) -s libs.tests -c $(_BuildConfig) $(crossArg) $(_nativeSanitizersArg) /p:TestAssemblies=false /p:RunNativeAotTestApps=true $(_officialBuildParameter) /bl:$(Build.SourcesDirectory)/artifacts/log/$(buildConfigUpper)/NativeAotTests.binlog ${{ parameters.extraTestArgs }}
displayName: Run NativeAot Library Tests
diff --git a/eng/pipelines/coreclr/templates/crossdac-build.yml b/eng/pipelines/coreclr/templates/crossdac-build.yml
index f0ac5d36f00475..a8accb9d2e3d28 100644
--- a/eng/pipelines/coreclr/templates/crossdac-build.yml
+++ b/eng/pipelines/coreclr/templates/crossdac-build.yml
@@ -22,10 +22,7 @@ steps:
[Parameter(Mandatory)][string]$targetDir
)
- if ('${{ parameters.archType }}' -ne '${{ parameters.hostArchType }}')
- {
- $crossDacDir = Join-Path $crossDacDir -ChildPath '${{ parameters.hostArchType }}'
- }
+ $crossDacDir = Join-Path $crossDacDir -ChildPath '${{ parameters.hostArchType }}'
$availableFiles = ls -File $crossDacDir
diff --git a/eng/pipelines/runtime-sanitized.yml b/eng/pipelines/runtime-sanitized.yml
index 32023c6fa9f127..3bc49fec690830 100644
--- a/eng/pipelines/runtime-sanitized.yml
+++ b/eng/pipelines/runtime-sanitized.yml
@@ -1,8 +1,14 @@
# This pipeline provides an easy mechanism for us to run runtime and libaries tests with native sanitizers enabled
-# without having to compilcate the runtime.yml pipeline. This pipeline is intended to be run on a rolling basis
-# but a schedule is yet to be determined.
+# without having to compilcate the runtime.yml pipeline.
trigger: none
+schedules:
+- cron: "0 11 * * 2"
+ displayName: Tuesday at 3:00 AM (UTC-8:00)
+ branches:
+ include:
+ - main
+
variables:
- template: /eng/pipelines/common/variables.yml
@@ -10,5 +16,95 @@ extends:
template: /eng/pipelines/common/templates/pipeline-with-resources.yml
parameters:
stages:
- - stage: Build
+ - stage: AddressSanitizer
jobs:
+ #
+ # Build the whole product with CoreCLR and run runtime tests with AddressSanitizer
+ #
+ - template: /eng/pipelines/common/platform-matrix.yml
+ parameters:
+ jobTemplate: /eng/pipelines/common/global-build-job.yml
+ helixQueuesTemplate: /eng/pipelines/coreclr/templates/helix-queues-setup.yml
+ buildConfig: Checked
+ runtimeFlavor: coreclr
+ platforms:
+ - linux_x64
+ - osx_x64
+ variables:
+ - name: _nativeSanitizersArg
+ value: -fsanitize address
+ jobParameters:
+ nameSuffix: CoreCLR_RuntimeTests
+ buildArgs: -s clr+libs -c $(_BuildConfig) $(_nativeSanitizersArg)
+ timeoutInMinutes: 300
+ # extra steps, run tests
+ extraStepsTemplate: /eng/pipelines/common/templates/runtimes/build-runtime-tests-and-send-to-helix.yml
+ extraStepsParameters:
+ creator: dotnet-bot
+ testRunNamePrefixSuffix: CoreCLR_$(_BuildConfig)
+ scenarios:
+ - normal
+ - no_tiered_compilation
+ extraVariablesTemplates:
+ - template: /eng/pipelines/common/templates/runtimes/test-variables.yml
+ parameters:
+ testGroup: outerloop
+ sanitizers: 'address'
+
+ #
+ # Build the whole product with CoreCLR and run libraries tests with AddressSanitizer
+ #
+ - template: /eng/pipelines/common/platform-matrix.yml
+ parameters:
+ jobTemplate: /eng/pipelines/common/global-build-job.yml
+ helixQueuesTemplate: /eng/pipelines/libraries/helix-queues-setup.yml
+ buildConfig: Debug
+ runtimeFlavor: coreclr
+ platforms:
+ - linux_x64
+ - osx_x64
+ variables:
+ - name: _nativeSanitizersArg
+ value: -fsanitize address
+ jobParameters:
+ testGroup: innerloop
+ nameSuffix: CoreCLR_LibrariesTests
+ buildArgs: -s clr+libs+libs.tests -c $(_BuildConfig) -rc Checked $(_nativeSanitizersArg) /p:ArchiveTests=true
+ timeoutInMinutes: 180
+ # extra steps, run tests
+ extraStepsTemplate: /eng/pipelines/libraries/helix.yml
+ extraStepsParameters:
+ creator: dotnet-bot
+ testRunNamePrefixSuffix: Libraries_$(_BuildConfig)
+ scenarios:
+ - normal
+
+ #
+ # NativeAOT release build and smoke tests with AddressSanitizer
+ #
+ - template: /eng/pipelines/common/platform-matrix.yml
+ parameters:
+ jobTemplate: /eng/pipelines/common/global-build-job.yml
+ helixQueuesTemplate: /eng/pipelines/coreclr/templates/helix-queues-setup.yml
+ buildConfig: release
+ platforms:
+ - linux_x64
+ - osx_x64
+ variables:
+ - name: _nativeSanitizersArg
+ value: -fsanitize address
+ jobParameters:
+ testGroup: innerloop
+ timeoutInMinutes: 120
+ nameSuffix: NativeAOT
+ buildArgs: -s clr.aot+host.native+libs -rc $(_BuildConfig) -lc Release -hc Release $(_nativeSanitizersArg)
+ extraStepsTemplate: /eng/pipelines/coreclr/nativeaot-post-build-steps.yml
+ extraStepsParameters:
+ creator: dotnet-bot
+ testBuildArgs: nativeaot tree nativeaot
+ liveLibrariesBuildConfig: Release
+ extraVariablesTemplates:
+ - template: /eng/pipelines/common/templates/runtimes/test-variables.yml
+ parameters:
+ sanitizers: 'address'
+ liveLibrariesBuildConfig: Release
diff --git a/eng/pipelines/runtime.yml b/eng/pipelines/runtime.yml
index 8edd9927a2c0a0..68b3a915ce6454 100644
--- a/eng/pipelines/runtime.yml
+++ b/eng/pipelines/runtime.yml
@@ -219,6 +219,7 @@ extends:
- template: /eng/pipelines/common/templates/runtimes/test-variables.yml
parameters:
testGroup: innerloop
+ liveLibrariesBuildConfig: Release
condition: >-
or(
eq(dependencies.evaluate_paths.outputs['SetPathVars_coreclr.containsChange'], true),
@@ -255,6 +256,7 @@ extends:
- template: /eng/pipelines/common/templates/runtimes/test-variables.yml
parameters:
testGroup: innerloop
+ liveLibrariesBuildConfig: Release
condition: >-
or(
eq(dependencies.evaluate_paths.outputs['SetPathVars_coreclr.containsChange'], true),
@@ -297,6 +299,7 @@ extends:
- template: /eng/pipelines/common/templates/runtimes/test-variables.yml
parameters:
testGroup: innerloop
+ liveLibrariesBuildConfig: Release
condition: >-
or(
eq(dependencies.evaluate_paths.outputs['SetPathVars_coreclr.containsChange'], true),
diff --git a/eng/testing/linker/project.csproj.template b/eng/testing/linker/project.csproj.template
index ab498732e2ebfc..2295ab9c0e3cbe 100644
--- a/eng/testing/linker/project.csproj.template
+++ b/eng/testing/linker/project.csproj.template
@@ -82,4 +82,5 @@
+
diff --git a/eng/testing/linker/trimmingTests.targets b/eng/testing/linker/trimmingTests.targets
index 24315195a66f01..e192887f54233b 100644
--- a/eng/testing/linker/trimmingTests.targets
+++ b/eng/testing/linker/trimmingTests.targets
@@ -1,4 +1,9 @@
+
+ $(CoreCLRILCompilerDir)
+ $(CoreCLRCrossILCompilerDir)
+
+
@@ -54,7 +59,7 @@
<_additionalProjectReferenceTemp Include="$(AdditionalProjectReferences)" />
<_additionalProjectReference Include="<ProjectReference Include="$(LibrariesProjectRoot)%(_additionalProjectReferenceTemp.Identity)\src\%(_additionalProjectReferenceTemp.Identity).csproj" SkipUseReferenceAssembly="true" />" />
-
+
<_additionalProjectReferencesString>@(_additionalProjectReference, '%0a')
@@ -66,7 +71,7 @@
<_switchesAsItems Include="%(TestConsoleApps.DisabledFeatureSwitches)" Value="false" />
<_switchesAsItems Include="%(TestConsoleApps.EnabledFeatureSwitches)" Value="true" />
-
+
<_propertiesAsItems Include="%(TestConsoleApps.DisabledProperties)" Value="false" />
<_propertiesAsItems Include="%(TestConsoleApps.EnabledProperties)" Value="true" />
@@ -87,7 +92,7 @@
.Replace('{MicrosoftNETILLinkTasksVersion}', '$(MicrosoftNETILLinkTasksVersion)')
.Replace('{ExtraTrimmerArgs}', '%(TestConsoleApps.ExtraTrimmerArgs)')
.Replace('{AdditionalProperties}', '$(_additionalPropertiesString)')
- .Replace('{IlcToolsPath}', '$(CoreCLRILCompilerDir)')
+ .Replace('{IlcToolsPath}', '$(IlcToolsPath)')
.Replace('{IlcBuildTasksPath}', '$(CoreCLRILCompilerDir)netstandard/ILCompiler.Build.Tasks.dll')
.Replace('{IlcSdkPath}', '$(CoreCLRAotSdkDir)')
.Replace('{IlcFrameworkPath}', '$(MicrosoftNetCoreAppRuntimePackRidLibTfmDir)')
@@ -108,6 +113,7 @@
.Replace('{MicrosoftNetCoreAppFrameworkName}', '$(MicrosoftNetCoreAppFrameworkName)')
.Replace('{MicrosoftNetCoreAppRefPackDir}', '$(MicrosoftNetCoreAppRefPackDir)')
.Replace('{MicrosoftNetCoreAppRuntimePackDir}', '$(MicrosoftNetCoreAppRuntimePackDir)')
+ .Replace('{NativeSanitizersTargets}', '$(RepositoryEngineeringDir)nativeSanitizers.targets')
.Replace('{AppHostSourcePath}', '$(AppHostSourcePath)')
.Replace('{SingleFileHostSourcePath}', '$(SingleFileHostSourcePath)'))"
Overwrite="true" />
@@ -131,7 +137,7 @@
+ Properties="Configuration=$(Configuration);BuildProjectReferences=false;TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture)" />
$(CoreCLRILCompilerDir)
- $(CoreCLRCrossILCompilerDir)
+ $(CoreCLRCrossILCompilerDir)
$(ROOTFS_DIR)
$(CoreCLRILCompilerDir)netstandard/ILCompiler.Build.Tasks.dll
$(CoreCLRAotSdkDir)
diff --git a/src/coreclr/build-runtime.cmd b/src/coreclr/build-runtime.cmd
index a8fca255b86116..ec6887c78d84cb 100644
--- a/src/coreclr/build-runtime.cmd
+++ b/src/coreclr/build-runtime.cmd
@@ -65,12 +65,13 @@ set __UnprocessedBuildArgs=
set __BuildNative=1
set __RestoreOptData=1
set __HostArch=
-set __HostArch2=
set __PgoOptDataPath=
set __CMakeArgs=
set __Ninja=1
set __RequestedBuildComponents=
set __OutputRid=
+set __ExplicitHostArch=
+set __SubDir=
:Arg_Loop
if "%1" == "" goto ArgsDone
@@ -127,9 +128,10 @@ if [!__PassThroughArgs!]==[] (
set "__PassThroughArgs=%__PassThroughArgs% %1"
)
-if /i "%1" == "-hostarch" (set __HostArch=%2&shift&shift&goto Arg_Loop)
+if /i "%1" == "-hostarch" (set __HostArch=%2&set __ExplicitHostArch=1&shift&shift&goto Arg_Loop)
if /i "%1" == "-os" (set __TargetOS=%2&shift&shift&goto Arg_Loop)
if /i "%1" == "-outputrid" (set __OutputRid=%2&shift&shift&goto Arg_Loop)
+if /i "%1" == "-subdir" (set __SubDir=%2&shift&shift&goto Arg_Loop)
if /i "%1" == "-cmakeargs" (set __CMakeArgs=%2 %__CMakeArgs%&set __remainingArgs="!__remainingArgs:*%2=!"&shift&shift&goto Arg_Loop)
if /i "%1" == "-configureonly" (set __ConfigureOnly=1&set __BuildNative=1&shift&goto Arg_Loop)
@@ -142,6 +144,7 @@ if /i "%1" == "-pgoinstrument" (set __PgoInstrument=1&shift&goto Arg_Loop)
if /i "%1" == "-enforcepgo" (set __EnforcePgo=1&shift&goto Arg_Loop)
if /i "%1" == "-pgodatapath" (set __PgoOptDataPath=%2&set __PgoOptimize=1&shift&shift&goto Arg_Loop)
if /i "%1" == "-component" (set __RequestedBuildComponents=%__RequestedBuildComponents%-%2&set "__remainingArgs=!__remainingArgs:*%2=!"&shift&shift&goto Arg_Loop)
+if /i "%1" == "-fsanitize" (set __CMakeArgs=%__CMakeArgs% "-DCLR_CMAKE_ENABLE_SANITIZERS=%2"&shift&shift&goto Arg_Loop)
REM TODO these are deprecated remove them eventually
REM don't add more, use the - syntax instead
@@ -216,9 +219,15 @@ set "__ArtifactsIntermediatesDir=%__RepoRootDir%\artifacts\obj\coreclr\"
if "%__Ninja%"=="0" (set "__IntermediatesDir=%__IntermediatesDir%\ide")
set "__PackagesBinDir=%__BinDir%\.nuget"
+if "%__ExplicitHostArch%" == "1" (
+ set __BinDir=%__BinDir%\%__HostArch%
+ set __IntermediatesDir=%__IntermediatesDir%\%__HostArch%
+)
-if NOT "%__HostArch%" == "%__TargetArch%" set __BinDir=%__BinDir%\%__HostArch%
-if NOT "%__HostArch%" == "%__TargetArch%" set __IntermediatesDir=%__IntermediatesDir%\%__HostArch%
+if NOT "%__SubDir%"=="" (
+ set __BinDir=%__BinDir%\%__SubDir%
+ set __IntermediatesDir=%__IntermediatesDir%\%__SubDir%
+)
REM Generate path to be set for CMAKE_INSTALL_PREFIX to contain forward slash
set "__CMakeBinDir=%__BinDir%"
@@ -318,6 +327,9 @@ for /f "delims=" %%a in ("-%__RequestedBuildComponents%-") do (
if not "!string:-crosscomponents-=!"=="!string!" (
set __CMakeTarget=!__CMakeTarget! crosscomponents
)
+ if not "!string:-debug-=!"=="!string!" (
+ set __CMakeTarget=!__CMakeTarget! debug
+ )
)
if "!__CMakeTarget!" == "" (
set __CMakeTarget=install
@@ -353,8 +365,10 @@ if %__BuildNative% EQU 1 (
set __VCTargetArch=x86_arm64
)
- echo %__MsgPrefix%Using environment: "%__VCToolsRoot%\vcvarsall.bat" !__VCTargetArch!
- call "%__VCToolsRoot%\vcvarsall.bat" !__VCTargetArch!
+ if NOT DEFINED SkipVCEnvInit (
+ echo %__MsgPrefix%Using environment: "%__VCToolsRoot%\vcvarsall.bat" !__VCTargetArch!
+ call "%__VCToolsRoot%\vcvarsall.bat" !__VCTargetArch!
+ )
@if defined _echo @echo on
if defined __SkipConfigure goto SkipConfigure
@@ -555,6 +569,7 @@ echo -cmakeargs: user-settable additional arguments passed to CMake.
echo -configureonly: skip all builds; only run CMake ^(default: CMake and builds are run^)
echo -skipconfigure: skip CMake ^(default: CMake is run^)
echo -skipnative: skip building native components ^(default: native components are built^).
+echo -fsanitize ^: Enable the specified sanitizers. This script does not handle converting 'true' to the default sanitizers.
echo.
echo Examples:
echo build-runtime
diff --git a/src/coreclr/build-runtime.sh b/src/coreclr/build-runtime.sh
index 31c5cc286d530a..06f79ec34b420b 100755
--- a/src/coreclr/build-runtime.sh
+++ b/src/coreclr/build-runtime.sh
@@ -23,6 +23,7 @@ usage_list+=("-pgoinstrument: generate instrumented code for profile guided opti
usage_list+=("-skipcrossarchnative: Skip building cross-architecture native binaries.")
usage_list+=("-staticanalyzer: use scan_build static analyzer.")
usage_list+=("-component: Build individual components instead of the full project. Available options are 'hosts', 'jit', 'runtime', 'paltests', 'alljits', 'iltools', 'nativeaot', and 'spmi'. Can be specified multiple times.")
+usage_list+=("-subdir: Append a directory with the provided name to the obj and bin paths.")
setup_dirs_local()
{
@@ -53,6 +54,12 @@ handle_arguments_local() {
__RequestedBuildComponents="$__RequestedBuildComponents $2"
__ShiftArgs=1
;;
+
+ subdir|-subdir)
+ __SubDir="$2"
+ __ShiftArgs=1
+ ;;
+
*)
__UnprocessedBuildArgs="$__UnprocessedBuildArgs $1"
;;
@@ -97,6 +104,7 @@ __UseNinja=0
__VerboseBuild=0
__CMakeArgs=""
__RequestedBuildComponents=""
+__SubDir=""
source "$__ProjectRoot"/_build-commons.sh
@@ -121,6 +129,11 @@ if [[ "$__ExplicitHostArch" == 1 ]]; then
__BinDir="$__BinDir/$__HostArch"
fi
+if [[ -n "$__SubDir" ]]; then
+ __IntermediatesDir="$__IntermediatesDir/$__SubDir"
+ __BinDir="$__BinDir/$__SubDir"
+fi
+
# CI_SPECIFIC - On CI machines, $HOME may not be set. In such a case, create a subfolder and set the variable to set.
# This is needed by CLI to function.
if [[ -z "$HOME" ]]; then
diff --git a/src/coreclr/components.cmake b/src/coreclr/components.cmake
index 3eaa2c966bf32e..70dd081376f674 100644
--- a/src/coreclr/components.cmake
+++ b/src/coreclr/components.cmake
@@ -7,6 +7,7 @@ add_component(paltests paltests_install)
add_component(iltools)
add_component(nativeaot)
add_component(spmi)
+add_component(debug)
# Define coreclr_all as the fallback component and make every component depend on this component.
# iltools and paltests should be minimal subsets, so don't add a dependency on coreclr_misc
@@ -19,6 +20,9 @@ add_dependencies(runtime coreclr_misc)
# The runtime build requires the clrjit and iltools builds
add_dependencies(runtime jit iltools)
+# The runtime build requires the debugger tools builds
+add_dependencies(runtime debug)
+
add_dependencies(runtime hosts)
# The cross-components build is separate, so we don't need to add a dependency on coreclr_misc
diff --git a/src/coreclr/crossgen-corelib.proj b/src/coreclr/crossgen-corelib.proj
index 1d7eb27679749e..2dc62b8151a3ce 100644
--- a/src/coreclr/crossgen-corelib.proj
+++ b/src/coreclr/crossgen-corelib.proj
@@ -1,8 +1,12 @@
+
+ true
+
+
-
-
+
+
diff --git a/src/coreclr/dlls/mscordac/CMakeLists.txt b/src/coreclr/dlls/mscordac/CMakeLists.txt
index b736de536a798e..36124262f7f934 100644
--- a/src/coreclr/dlls/mscordac/CMakeLists.txt
+++ b/src/coreclr/dlls/mscordac/CMakeLists.txt
@@ -196,7 +196,7 @@ endif(CLR_CMAKE_HOST_UNIX)
target_link_libraries(mscordaccore PRIVATE ${COREDAC_LIBRARIES})
# add the install targets
-install_clr(TARGETS mscordaccore DESTINATIONS . sharedFramework COMPONENT runtime)
+install_clr(TARGETS mscordaccore DESTINATIONS . sharedFramework COMPONENT debug)
if(CLR_CMAKE_HOST_WIN32)
set(LONG_NAME_HOST_ARCH ${CLR_CMAKE_HOST_ARCH})
diff --git a/src/coreclr/dlls/mscordbi/CMakeLists.txt b/src/coreclr/dlls/mscordbi/CMakeLists.txt
index 9f8a442c1b55cb..1940f64e94b092 100644
--- a/src/coreclr/dlls/mscordbi/CMakeLists.txt
+++ b/src/coreclr/dlls/mscordbi/CMakeLists.txt
@@ -55,6 +55,7 @@ else(CLR_CMAKE_HOST_WIN32)
endif(CLR_CMAKE_HOST_WIN32)
add_library_clr(mscordbi SHARED ${MSCORDBI_SOURCES})
+set_target_properties(mscordbi PROPERTIES DBI_COMPONENT TRUE)
target_precompile_headers(mscordbi PRIVATE $<$:stdafx.h>)
if(CLR_CMAKE_HOST_UNIX)
@@ -125,4 +126,4 @@ elseif(CLR_CMAKE_HOST_UNIX)
endif(CLR_CMAKE_HOST_WIN32)
# add the install targets
-install_clr(TARGETS mscordbi DESTINATIONS . sharedFramework COMPONENT runtime)
+install_clr(TARGETS mscordbi DESTINATIONS . sharedFramework COMPONENT debug)
diff --git a/src/coreclr/enablesanitizers.sh b/src/coreclr/enablesanitizers.sh
index c79ef8c69ddf3f..a5f88be30636de 100755
--- a/src/coreclr/enablesanitizers.sh
+++ b/src/coreclr/enablesanitizers.sh
@@ -9,8 +9,7 @@ if [ $# -eq 0 ]; then
else
echo " cd $(dirname $0);. enablesanitizers.sh [options]; cd -"
fi
- echo "Usage: [asan] [ubsan] [lsan] [all] [off] [clangx.y]"
- echo " asan: optional argument to enable Address Sanitizer."
+ echo "Usage: [ubsan] [lsan] [all] [off] [clangx.y]"
echo " ubsan: optional argument to enable Undefined Behavior Sanitizer."
echo " lsan - optional argument to enable memory Leak Sanitizer."
echo " all - optional argument to enable asan, ubsan and lsan."
@@ -21,7 +20,6 @@ else
__ClangMajorVersion=3
__ClangMinorVersion=6
- __EnableASan=0
__EnableUBSan=0
__EnableLSan=0
__TurnOff=0
@@ -32,18 +30,13 @@ else
do
lowerI="$(echo $i | tr "[:upper:]" "[:lower:]")"
case $lowerI in
- asan)
- __EnableASan=1
- ;;
ubsan)
__EnableUBSan=1
;;
lsan)
- __EnableASan=1
__EnableLSan=1
;;
all)
- __EnableASan=1
__EnableUBSan=1
__EnableLSan=1
;;
@@ -83,22 +76,16 @@ else
unset DEBUG_SANITIZERS
echo "Setting DEBUG_SANITIZERS="
else
- # for now, specify alloc_dealloc_mismatch=0 as there are too many error reports that are not an issue.
- # Also specify use_sigaltstack=0 as coreclr uses own alternate stack for signal handlers
- ASAN_OPTIONS="symbolize=1 alloc_dealloc_mismatch=0 use_sigaltstack=0"
# when Clang 3.8 available, add: suppressions=$(readlink -f sanitizersuppressions.txt)
UBSAN_OPTIONS="print_stacktrace=1"
- if [[ "$__EnableASan" == 1 ]]; then
- __Options="$__Options asan"
- fi
- if [[ "$__EnableUBSan" == 1 ]]; then
+ if [ $__EnableUBSan == 1 ]; then
__Options="$__Options ubsan"
fi
- if [[ "$__EnableLSan" == 1 ]]; then
- ASAN_OPTIONS="$ASAN_OPTIONS detect_leaks=1"
+ if [ $__EnableLSan == 1 ]; then
+ LSAN_OPTIONS="detect_leaks=1"
else
- ASAN_OPTIONS="$ASAN_OPTIONS detect_leaks=0"
+ LSAN_OPTIONS="detect_leaks=0"
fi
# passed to build.sh
@@ -128,7 +115,6 @@ else
unset __ClangMajorVersion
unset __ClangMinorVersion
- unset __EnableASan
unset __EnableUBSan
unset __EnableLSan
unset __TurnOff
diff --git a/src/coreclr/hosts/corerun/CMakeLists.txt b/src/coreclr/hosts/corerun/CMakeLists.txt
index 86ae704780d96c..9540fc3b006b9d 100644
--- a/src/coreclr/hosts/corerun/CMakeLists.txt
+++ b/src/coreclr/hosts/corerun/CMakeLists.txt
@@ -39,3 +39,8 @@ else(CLR_CMAKE_HOST_WIN32)
endif(CLR_CMAKE_HOST_WIN32)
install_clr(TARGETS corerun DESTINATIONS . COMPONENT hosts)
+
+# If there's a dynamic ASAN runtime, then install it in the directory where we put our executable.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ install(FILES ${ASAN_RUNTIME} DESTINATION .)
+endif()
\ No newline at end of file
diff --git a/src/coreclr/nativeaot/Bootstrap/CMakeLists.txt b/src/coreclr/nativeaot/Bootstrap/CMakeLists.txt
index 02fb30aad9f0c3..081da0b05a4c91 100644
--- a/src/coreclr/nativeaot/Bootstrap/CMakeLists.txt
+++ b/src/coreclr/nativeaot/Bootstrap/CMakeLists.txt
@@ -1,2 +1,20 @@
+
+function(install_bootstrapper_object targetName destination)
+ add_dependencies(nativeaot ${targetName})
+ if (MSVC)
+ set_target_properties(${targetName} PROPERTIES COMPILE_PDB_NAME ${targetName})
+ endif()
+ if (MSVC)
+ install (FILES $ DESTINATION ${destination} COMPONENT nativeaot RENAME ${targetName}.obj)
+ if (CMAKE_GENERATOR MATCHES "Visual Studio")
+ install (FILES ${CMAKE_CURRENT_BINARY_DIR}/$/${targetName}.pdb DESTINATION ${destination} COMPONENT nativeaot)
+ else()
+ install (FILES ${CMAKE_CURRENT_BINARY_DIR}/${targetName}.pdb DESTINATION ${destination} COMPONENT nativeaot)
+ endif()
+ else()
+ install (FILES $ DESTINATION ${destination} COMPONENT nativeaot RENAME lib${targetName}.o)
+ endif()
+endfunction()
+
add_subdirectory(base)
add_subdirectory(dll)
diff --git a/src/coreclr/nativeaot/Bootstrap/base/CMakeLists.txt b/src/coreclr/nativeaot/Bootstrap/base/CMakeLists.txt
index 370dfd0712b218..3ffc81ac648b09 100644
--- a/src/coreclr/nativeaot/Bootstrap/base/CMakeLists.txt
+++ b/src/coreclr/nativeaot/Bootstrap/base/CMakeLists.txt
@@ -4,13 +4,14 @@ set(SOURCES
../main.cpp
)
-add_library(bootstrapper STATIC ${SOURCES})
+add_library(bootstrapper OBJECT ${SOURCES})
+set_target_properties(bootstrapper PROPERTIES OUTPUT_NAME bootstrapper)
-install_static_library(bootstrapper aotsdk nativeaot)
+install_bootstrapper_object(bootstrapper aotsdk)
if (CLR_CMAKE_TARGET_WIN32)
- add_library(bootstrapper.GuardCF STATIC ${SOURCES})
- install_static_library(bootstrapper.GuardCF aotsdk nativeaot)
+ add_library(bootstrapper.GuardCF OBJECT ${SOURCES})
+ install_bootstrapper_object(bootstrapper.GuardCF aotsdk)
target_compile_options(bootstrapper.GuardCF PRIVATE $<$,$>:/guard:cf>)
else()
add_library(stdc++compat STATIC ../stdcppshim.cpp)
diff --git a/src/coreclr/nativeaot/Bootstrap/dll/CMakeLists.txt b/src/coreclr/nativeaot/Bootstrap/dll/CMakeLists.txt
index b1a99ebc3b2257..14eb3ece8e1e04 100644
--- a/src/coreclr/nativeaot/Bootstrap/dll/CMakeLists.txt
+++ b/src/coreclr/nativeaot/Bootstrap/dll/CMakeLists.txt
@@ -8,10 +8,10 @@ set(SOURCES
add_library(bootstrapperdll STATIC ${SOURCES})
-install_static_library(bootstrapperdll aotsdk nativeaot)
+install_bootstrapper_object(bootstrapperdll aotsdk)
if (CLR_CMAKE_TARGET_WIN32)
add_library(bootstrapperdll.GuardCF STATIC ${SOURCES})
- install_static_library(bootstrapperdll.GuardCF aotsdk nativeaot)
+ install_bootstrapper_object(bootstrapperdll.GuardCF aotsdk)
target_compile_options(bootstrapperdll.GuardCF PRIVATE $<$,$>:/guard:cf>)
endif()
diff --git a/src/coreclr/nativeaot/Bootstrap/main.cpp b/src/coreclr/nativeaot/Bootstrap/main.cpp
index 5e30ae1f0f495b..8115fc870c23e3 100644
--- a/src/coreclr/nativeaot/Bootstrap/main.cpp
+++ b/src/coreclr/nativeaot/Bootstrap/main.cpp
@@ -2,6 +2,7 @@
// The .NET Foundation licenses this file to you under the MIT license.
#include
+#include "minipal/utils.h"
//
// This is the mechanism whereby multiple linked modules contribute their global data for initialization at
@@ -217,6 +218,12 @@ int main(int argc, char* argv[])
return __managed__Main(argc, argv);
}
+
+// We need to build the bootstrapper as a single object file, to ensure
+// the linker can detect that we have ASAN components early enough in the build.
+// Include our asan support sources for executable projects here to ensure they
+// are compiled into the bootstrapper object.
+#include "minipal/asansupport.cpp"
#endif // !NATIVEAOT_DLL
#ifdef NATIVEAOT_DLL
diff --git a/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Unix.targets b/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Unix.targets
index bb1b8c435a1377..e0c506bd012680 100644
--- a/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Unix.targets
+++ b/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Unix.targets
@@ -55,8 +55,8 @@ The .NET Foundation licenses this file to you under the MIT license.
-
-
+
+
diff --git a/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Windows.targets b/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Windows.targets
index 9512bf826c40b0..5c6dd32cb6a4be 100644
--- a/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Windows.targets
+++ b/src/coreclr/nativeaot/BuildIntegration/Microsoft.NETCore.Native.Windows.targets
@@ -16,7 +16,9 @@ The .NET Foundation licenses this file to you under the MIT license.
link
lib
+ .obj
.lib
+ .GuardCF.obj
.GuardCF.lib
Runtime.WorkstationGC
Runtime.ServerGC
@@ -35,7 +37,7 @@ The .NET Foundation licenses this file to you under the MIT license.
-
+
diff --git a/src/coreclr/nativeaot/Runtime/windows/PalRedhawkMinWin.cpp b/src/coreclr/nativeaot/Runtime/windows/PalRedhawkMinWin.cpp
index 6691df67ada460..902483765b20d6 100644
--- a/src/coreclr/nativeaot/Runtime/windows/PalRedhawkMinWin.cpp
+++ b/src/coreclr/nativeaot/Runtime/windows/PalRedhawkMinWin.cpp
@@ -438,6 +438,7 @@ REDHAWK_PALEXPORT _Success_(return) bool REDHAWK_PALAPI PalSetThreadContext(HAND
REDHAWK_PALEXPORT void REDHAWK_PALAPI PalRestoreContext(CONTEXT * pCtx)
{
+ __asan_handle_no_return();
RtlRestoreContext(pCtx, NULL);
}
diff --git a/src/coreclr/pal/src/arch/amd64/context2.S b/src/coreclr/pal/src/arch/amd64/context2.S
index 87a1277270c49b..dba772f9dbbf5e 100644
--- a/src/coreclr/pal/src/arch/amd64/context2.S
+++ b/src/coreclr/pal/src/arch/amd64/context2.S
@@ -89,7 +89,7 @@ LEAF_ENTRY RtlRestoreContext, _TEXT
push_nonvol_reg rbp
alloc_stack (IRetFrameLengthAligned)
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
test BYTE PTR [rdi + CONTEXT_ContextFlags], CONTEXT_CONTROL
je LOCAL_LABEL(Restore_CONTEXT_FLOATING_POINT)
diff --git a/src/coreclr/pal/src/arch/amd64/exceptionhelper.S b/src/coreclr/pal/src/arch/amd64/exceptionhelper.S
index 1e61336bfd5408..ac5dc157a104e3 100644
--- a/src/coreclr/pal/src/arch/amd64/exceptionhelper.S
+++ b/src/coreclr/pal/src/arch/amd64/exceptionhelper.S
@@ -13,7 +13,7 @@
// Then it uses the ThrowExceptionHelper to throw the passed in exception from that context.
// EXTERN_C void ThrowExceptionFromContextInternal(CONTEXT* context, PAL_SEHException* ex);
LEAF_ENTRY ThrowExceptionFromContextInternal, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
// Need to call __asan_handle_no_return explicitly here because we re-initialize RSP before
// throwing exception in ThrowExceptionHelper
push_nonvol_reg rdi
diff --git a/src/coreclr/pal/src/arch/arm/context2.S b/src/coreclr/pal/src/arch/arm/context2.S
index edb5d35bf1e40c..32983c196969fb 100644
--- a/src/coreclr/pal/src/arch/arm/context2.S
+++ b/src/coreclr/pal/src/arch/arm/context2.S
@@ -118,7 +118,7 @@ LEAF_END RtlCaptureContext, _TEXT
LEAF_ENTRY RtlRestoreContext, _TEXT
END_PROLOGUE
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
ldr r2, [r0, #(CONTEXT_ContextFlags)]
tst r2, #(CONTEXT_CONTROL)
beq LOCAL_LABEL(Restore_CONTEXT_FLOATING_POINT)
diff --git a/src/coreclr/pal/src/arch/arm/exceptionhelper.S b/src/coreclr/pal/src/arch/arm/exceptionhelper.S
index 18878894b0602b..e450af68ec5937 100644
--- a/src/coreclr/pal/src/arch/arm/exceptionhelper.S
+++ b/src/coreclr/pal/src/arch/arm/exceptionhelper.S
@@ -12,7 +12,7 @@
// EXTERN_C void ThrowExceptionFromContextInternal(CONTEXT* context, PAL_SEHException* ex);
LEAF_ENTRY ThrowExceptionFromContextInternal, _TEXT
// Ported from src/pal/src/arch/amd64/exceptionhelper.S
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
// Need to call __asan_handle_no_return explicitly here because we re-initialize SP before
// throwing exception in ThrowExceptionHelper
push_nonvol_reg "{r0, r1}"
diff --git a/src/coreclr/pal/src/arch/arm64/context2.S b/src/coreclr/pal/src/arch/arm64/context2.S
index ecbb10ca8fdea4..23bc0c065581e0 100644
--- a/src/coreclr/pal/src/arch/arm64/context2.S
+++ b/src/coreclr/pal/src/arch/arm64/context2.S
@@ -135,7 +135,7 @@ LEAF_END RtlCaptureContext, _TEXT
//
LEAF_ENTRY RtlRestoreContext, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
ldr w17, [x0, #(CONTEXT_ContextFlags)]
tbz w17, #CONTEXT_CONTROL_BIT, LOCAL_LABEL(Restore_CONTEXT_FLOATING_POINT)
@@ -220,7 +220,7 @@ LEAF_END RtlRestoreContext, _TEXT
// x1: Exception*
//
LEAF_ENTRY RestoreCompleteContext, _TEXT
- // We cannot restore all registers in the user mode code, so we rely on a help from kernel here.
+ // We cannot restore all registers in the user mode code, so we rely on a help from kernel here.
// The following instruction is an undefined instruction. In the hardware exception handler, we check
// if the faulting address is the RtlRestoreContext and in case it is, we update the context of
// the faulting thread using the CONTEXT pointed to by the x0 register.
diff --git a/src/coreclr/pal/src/arch/arm64/exceptionhelper.S b/src/coreclr/pal/src/arch/arm64/exceptionhelper.S
index 7ad1ae4c58b267..5690a40f9c30d7 100644
--- a/src/coreclr/pal/src/arch/arm64/exceptionhelper.S
+++ b/src/coreclr/pal/src/arch/arm64/exceptionhelper.S
@@ -11,7 +11,7 @@
// Then it uses the ThrowExceptionHelper to throw the passed in exception from that context.
// EXTERN_C void ThrowExceptionFromContextInternal(CONTEXT* context, PAL_SEHException* ex);
LEAF_ENTRY ThrowExceptionFromContextInternal, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
// Need to call __asan_handle_no_return explicitly here because we re-initialize SP before
// throwing exception in ThrowExceptionHelper
stp x0, x1, [sp, -16]!
diff --git a/src/coreclr/pal/src/arch/i386/context2.S b/src/coreclr/pal/src/arch/i386/context2.S
index bfcc25b09f403c..cf5b464c27d0ce 100644
--- a/src/coreclr/pal/src/arch/i386/context2.S
+++ b/src/coreclr/pal/src/arch/i386/context2.S
@@ -94,7 +94,7 @@ LEAF_END RtlCaptureContext, _TEXT
LEAF_ENTRY RtlRestoreContext, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
call EXTERNAL_C_FUNC(__asan_handle_no_return)
#endif
mov eax, [esp + 4]
diff --git a/src/coreclr/pal/src/arch/i386/exceptionhelper.S b/src/coreclr/pal/src/arch/i386/exceptionhelper.S
index 9bada09b2cfd35..aec51ceb6d6504 100644
--- a/src/coreclr/pal/src/arch/i386/exceptionhelper.S
+++ b/src/coreclr/pal/src/arch/i386/exceptionhelper.S
@@ -17,7 +17,7 @@
//////////////////////////////////////////////////////////////////////////
LEAF_ENTRY ThrowExceptionFromContextInternal, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
// Need to call __asan_handle_no_return explicitly here because we re-initialize ESP before
// throwing exception in ThrowExceptionHelper
call EXTERNAL_C_FUNC(__asan_handle_no_return)
diff --git a/src/coreclr/pal/src/arch/loongarch64/context2.S b/src/coreclr/pal/src/arch/loongarch64/context2.S
index 97e02574fb4365..701bd39fb8b385 100644
--- a/src/coreclr/pal/src/arch/loongarch64/context2.S
+++ b/src/coreclr/pal/src/arch/loongarch64/context2.S
@@ -14,7 +14,7 @@
// a1: Exception*
//
LEAF_ENTRY RtlRestoreContext, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
ld.w $r21, $a0, CONTEXT_ContextFlags
ext $r21, $r21, CONTEXT_FLOATING_POINT_BIT, 1
beq $r21, $r0, LOCAL_LABEL(Restore_CONTEXT_FLOATING_POINT)
diff --git a/src/coreclr/pal/src/arch/loongarch64/exceptionhelper.S b/src/coreclr/pal/src/arch/loongarch64/exceptionhelper.S
index 157e4149df5eb4..b86450da1d0672 100644
--- a/src/coreclr/pal/src/arch/loongarch64/exceptionhelper.S
+++ b/src/coreclr/pal/src/arch/loongarch64/exceptionhelper.S
@@ -11,7 +11,7 @@
// Then it uses the ThrowExceptionHelper to throw the passed in exception from that context.
// EXTERN_C void ThrowExceptionFromContextInternal(CONTEXT* context, PAL_SEHException* ex);
LEAF_ENTRY ThrowExceptionFromContextInternal, _TEXT
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
#pragma error("LLVM v3.9 ASAN unimplemented on LOONGARCH yet")
#endif
addi.d $sp, $sp, -16
diff --git a/src/coreclr/pal/src/exception/machexception.cpp b/src/coreclr/pal/src/exception/machexception.cpp
index bce0ae4774a439..50db83248fe7ac 100644
--- a/src/coreclr/pal/src/exception/machexception.cpp
+++ b/src/coreclr/pal/src/exception/machexception.cpp
@@ -31,6 +31,7 @@ SET_DEFAULT_DEBUG_CHANNEL(EXCEPT); // some headers have code with asserts, so do
#include "pal/virtual.h"
#include "pal/map.hpp"
#include "pal/environ.h"
+#include
#include "machmessage.h"
@@ -356,27 +357,23 @@ PAL_ERROR CorUnix::CPalThread::DisableMachExceptions()
return palError;
}
-#if defined(HOST_AMD64)
-// Since HijackFaultingThread pushed the context, exception record and info on the stack, we need to adjust the
-// signature of PAL_DispatchException such that the corresponding arguments are considered to be on the stack
-// per GCC64 calling convention rules. Hence, the first 6 dummy arguments (corresponding to RDI, RSI, RDX,RCX, R8, R9).
-extern "C"
-void PAL_DispatchException(DWORD64 dwRDI, DWORD64 dwRSI, DWORD64 dwRDX, DWORD64 dwRCX, DWORD64 dwR8, DWORD64 dwR9, PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachExceptionInfo *pMachExceptionInfo)
-#elif defined(HOST_ARM64)
-
+#if defined(HOST_ARM64)
extern "C"
void
RestoreCompleteContext(
PCONTEXT ContextRecord,
PEXCEPTION_RECORD ExceptionRecord
);
-
-extern "C"
-void PAL_DispatchException(PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachExceptionInfo *pMachExceptionInfo)
#endif
-{
- CPalThread *pThread = InternalGetCurrentThread();
+__attribute__((noinline))
+static void PAL_DispatchExceptionInner(PCONTEXT pContext, PEXCEPTION_RECORD pExRecord)
+{
+ // Stash the inner context record into a local in a frame other than PAL_DispatchException
+ // to ensure we have a compiler-defined callee stack frame state to record the context record
+ // local before we call SEHProcessException. The instrumentation introduced by native sanitizers
+ // doesn't interface that well with the fake caller frames we define for PAL_DispatchException,
+ // but they work fine for any callees of PAL_DispatchException.
CONTEXT *contextRecord = pContext;
g_hardware_exception_context_locvar_offset = (int)((char*)&contextRecord - (char*)__builtin_frame_address(0));
@@ -400,6 +397,7 @@ void PAL_DispatchException(PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachE
if (continueExecution)
{
+ __asan_handle_no_return();
#if defined(HOST_ARM64)
// RtlRestoreContext assembly corrupts X16 & X17, so it cannot be
// used for GCStress=C restore
@@ -408,6 +406,28 @@ void PAL_DispatchException(PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachE
RtlRestoreContext(pContext, pExRecord);
#endif
}
+}
+
+#if defined(HOST_AMD64)
+// Since HijackFaultingThread pushed the context, exception record and info on the stack, we need to adjust the
+// signature of PAL_DispatchException such that the corresponding arguments are considered to be on the stack
+// per GCC64 calling convention rules. Hence, the first 6 dummy arguments (corresponding to RDI, RSI, RDX,RCX, R8, R9).
+extern "C"
+void PAL_DispatchException(DWORD64 dwRDI, DWORD64 dwRSI, DWORD64 dwRDX, DWORD64 dwRCX, DWORD64 dwR8, DWORD64 dwR9, PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachExceptionInfo *pMachExceptionInfo)
+#elif defined(HOST_ARM64)
+
+extern "C"
+void PAL_DispatchException(PCONTEXT pContext, PEXCEPTION_RECORD pExRecord, MachExceptionInfo *pMachExceptionInfo)
+#endif
+{
+ // At the time of executing this function, this thread's stack is a lie.
+ // This frame and the calling frame were never actually pushed onto the stack
+ // and were synthetically added by HijackFaultingThread.
+ // We need to let ASAN know that its stack tracking is out of date.
+ __asan_handle_no_return();
+ CPalThread *pThread = InternalGetCurrentThread();
+
+ PAL_DispatchExceptionInner(pContext, pExRecord);
// Send the forward request to the exception thread to process
MachMessage sSendMessage;
diff --git a/src/coreclr/pal/src/thread/thread.cpp b/src/coreclr/pal/src/thread/thread.cpp
index 0daa011e6fc636..90501bbafbde56 100644
--- a/src/coreclr/pal/src/thread/thread.cpp
+++ b/src/coreclr/pal/src/thread/thread.cpp
@@ -2449,7 +2449,7 @@ CPalThread::EnsureSignalAlternateStack()
// We include the size of the SignalHandlerWorkerReturnPoint in the alternate stack size since the
// context contained in it is large and the SIGSTKSZ was not sufficient on ARM64 during testing.
int altStackSize = SIGSTKSZ + ALIGN_UP(sizeof(SignalHandlerWorkerReturnPoint), 16) + GetVirtualPageSize();
-#ifdef HAS_ASAN
+#ifdef HAS_ADDRESS_SANITIZER
// Asan also uses alternate stack so we increase its size on the SIGSTKSZ * 4 that enough for asan
// (see kAltStackSize in compiler-rt/lib/sanitizer_common/sanitizer_posix_libcdep.cc)
altStackSize += SIGSTKSZ * 4;
diff --git a/src/coreclr/runtime.proj b/src/coreclr/runtime.proj
index 0b936f4579c56f..4164484606c1ba 100644
--- a/src/coreclr/runtime.proj
+++ b/src/coreclr/runtime.proj
@@ -1,7 +1,7 @@
- ClrFullNativeBuild;ClrRuntimeSubset;ClrJitSubset;ClrPalTestsSubset;ClrAllJitsSubset;ClrILToolsSubset;ClrNativeAotSubset;ClrSpmiSubset;ClrCrossComponentsSubset;HostArchitecture;PgoInstrument;NativeOptimizationDataSupported;CMakeArgs
+ ClrFullNativeBuild;ClrRuntimeSubset;ClrJitSubset;ClrPalTestsSubset;ClrAllJitsSubset;ClrILToolsSubset;ClrNativeAotSubset;ClrSpmiSubset;ClrCrossComponentsSubset;ClrDebugSubset;HostArchitecture;PgoInstrument;NativeOptimizationDataSupported;CMakeArgs
<_IcuDir Condition="'$(PkgMicrosoft_NETCore_Runtime_ICU_Transport)' != ''">$(PkgMicrosoft_NETCore_Runtime_ICU_Transport)/runtimes/$(TargetOS)-$(TargetArchitecture)$(_RuntimeVariant)/native
<_BuildNativeTargetOS>$(TargetOS)
@@ -22,8 +22,9 @@
DependsOnTargets="GetPgoDataPackagePath"
BeforeTargets="Build">
+ <_CMakeArgs Include="$(CMakeArgs)" />
+ <_CoreClrBuildArg Include="@(_CMakeArgs->'-cmakeargs "%(Identity)"')" />
<_CoreClrBuildArg Condition="'$(TargetArchitecture)' != ''" Include="-$(TargetArchitecture)" />
- <_CoreClrBuildArg Condition="'$(CMakeArgs)' != ''" Include="-cmakeargs "$(CMakeArgs)"" />
<_CoreClrBuildArg Include="-$(Configuration.ToLower())" />
<_CoreClrBuildArg Include="$(Compiler)" />
<_CoreClrBuildArg Condition="'$(ConfigureOnly)' == 'true'" Include="-configureonly" />
@@ -45,8 +46,10 @@
<_CoreClrBuildArg Condition="'$(PgoInstrument)' == 'true'" Include="-pgoinstrument" />
<_CoreClrBuildArg Condition="'$(NativeOptimizationDataSupported)' == 'true' and '$(NoPgoOptimize)' != 'true' and '$(PgoInstrument)' != 'true'" Include="-pgodatapath "$(PgoPackagePath)"" />
<_CoreClrBuildArg Condition="'$(HostArchitecture)' != ''" Include="-hostarch $(HostArchitecture)" />
+ <_CoreClrBuildArg Condition="'$(EnableNativeSanitizers)' != ''" Include="-fsanitize $(EnableNativeSanitizers)" />
<_CoreClrBuildArg Condition="'$(HostCrossOS)' != ''" Include="-hostos $(HostCrossOS)" />
<_CoreClrBuildArg Include="-outputrid $(OutputRID)" />
+ <_CoreClrBuildArg Condition="'$(BuildSubdirectory)' != ''" Include="-subdir $(BuildSubdirectory)" />
@@ -59,6 +62,7 @@
<_CoreClrBuildArg Condition="'$(ClrNativeAotSubset)' == 'true'" Include="-component nativeaot" />
<_CoreClrBuildArg Condition="'$(ClrSpmiSubset)' == 'true'" Include="-component spmi" />
<_CoreClrBuildArg Condition="'$(ClrCrossComponentsSubset)' == 'true'" Include="-component crosscomponents" />
+ <_CoreClrBuildArg Condition="'$(ClrDebugSubset)' == 'true'" Include="-component debug" />
@@ -90,4 +94,6 @@
+
+
diff --git a/src/coreclr/tools/aot/crossgen2/crossgen2.csproj b/src/coreclr/tools/aot/crossgen2/crossgen2.csproj
index 3702d329007765..199ec842608eb7 100644
--- a/src/coreclr/tools/aot/crossgen2/crossgen2.csproj
+++ b/src/coreclr/tools/aot/crossgen2/crossgen2.csproj
@@ -30,7 +30,7 @@
$(CoreCLRILCompilerDir)
- $(CoreCLRCrossILCompilerDir)
+ $(CoreCLRCrossILCompilerDir)
$(ROOTFS_DIR)
$(CoreCLRILCompilerDir)netstandard/ILCompiler.Build.Tasks.dll
$(CoreCLRAotSdkDir)
@@ -46,6 +46,7 @@
+
Esp, Ebx, Esi, Edi, Ebp, and Eip are initialized
_CallJitEHFilterHelper@8 PROC public
+ ; Call ___asan_handle_no_return here as we touch registers that ASAN uses.
+ifdef HAS_ADDRESS_SANITIZER
+ call ___asan_handle_no_return
+endif
push ebp
mov ebp, esp
push ebx
@@ -334,6 +346,10 @@ _CallJitEHFilterHelper@8 ENDP
; void __stdcall CallJITEHFinallyHelper(size_t *pShadowSP, EHContext *pContext);
; on entry, only the pContext->Esp, Ebx, Esi, Edi, Ebp, and Eip are initialized
_CallJitEHFinallyHelper@8 PROC public
+ ; Call ___asan_handle_no_return here as we touch registers that ASAN uses.
+ifdef HAS_ADDRESS_SANITIZER
+ call ___asan_handle_no_return
+endif
push ebp
mov ebp, esp
push ebx
diff --git a/src/coreclr/vm/i386/jitinterfacex86.cpp b/src/coreclr/vm/i386/jitinterfacex86.cpp
index 7e5c59135b85c8..e51a324813ef48 100644
--- a/src/coreclr/vm/i386/jitinterfacex86.cpp
+++ b/src/coreclr/vm/i386/jitinterfacex86.cpp
@@ -962,18 +962,11 @@ void InitJITHelpers1()
// Get CPU features and check for SSE2 support.
// This code should eventually probably be moved into codeman.cpp,
// where we set the cpu feature flags for the JIT based on CPU type and features.
- DWORD dwCPUFeaturesECX;
- DWORD dwCPUFeaturesEDX;
+ int cpuFeatures[4];
+ __cpuid(cpuFeatures, 1);
- __asm
- {
- pushad
- mov eax, 1
- cpuid
- mov dwCPUFeaturesECX, ecx
- mov dwCPUFeaturesEDX, edx
- popad
- }
+ DWORD dwCPUFeaturesECX = cpuFeatures[2];
+ DWORD dwCPUFeaturesEDX = cpuFeatures[3];
// If bit 26 (SSE2) is set, then we can use the SSE2 flavors
// and faster x87 implementation for the P4 of Dbl2Lng.
diff --git a/src/coreclr/vm/i386/stublinkerx86.cpp b/src/coreclr/vm/i386/stublinkerx86.cpp
index fde6801c289b6d..76d888c0c52756 100644
--- a/src/coreclr/vm/i386/stublinkerx86.cpp
+++ b/src/coreclr/vm/i386/stublinkerx86.cpp
@@ -77,7 +77,11 @@ extern "C" VOID __cdecl DebugCheckStubUnwindInfo();
#endif // TARGET_AMD64
#ifdef FEATURE_COMINTEROP
-Thread* __stdcall CreateThreadBlockReturnHr(ComMethodFrame *pFrame);
+// Use a type alias as MSVC has issues parsing the pointer, the calling convention, and the declspec
+// in the same signature.
+// Disable ASAN here as this method uses inline assembly and touches registers that ASAN uses.
+using ThreadPointer = Thread*;
+ThreadPointer DISABLE_ASAN __stdcall CreateThreadBlockReturnHr(ComMethodFrame *pFrame);
#endif
@@ -4913,7 +4917,7 @@ VOID StubLinkerCPU::EmitDebugBreak()
// global optimizations.
#pragma warning (disable : 4731)
#endif // _MSC_VER
-Thread* __stdcall CreateThreadBlockReturnHr(ComMethodFrame *pFrame)
+ThreadPointer __stdcall CreateThreadBlockReturnHr(ComMethodFrame *pFrame)
{
WRAPPER_NO_CONTRACT;
@@ -4931,6 +4935,10 @@ Thread* __stdcall CreateThreadBlockReturnHr(ComMethodFrame *pFrame)
UINT numArgStackBytes = pFrame->GetNumCallerStackBytes();
unsigned frameSize = sizeof(Frame) + sizeof(LPVOID);
LPBYTE iEsp = ((LPBYTE)pFrame) + ComMethodFrame::GetOffsetOfCalleeSavedRegisters();
+
+ // Let ASAN that we aren't going to return so it can do some cleanup
+ __asan_handle_no_return();
+
__asm
{
mov eax, hr
diff --git a/src/coreclr/vm/jithelpers.cpp b/src/coreclr/vm/jithelpers.cpp
index d5945f36582bbe..e78f312ea3f589 100644
--- a/src/coreclr/vm/jithelpers.cpp
+++ b/src/coreclr/vm/jithelpers.cpp
@@ -5658,6 +5658,7 @@ HCIMPL1(VOID, JIT_PartialCompilationPatchpoint, int ilOffset)
::SetLastError(dwLastError);
// Transition!
+ __asan_handle_no_return();
RtlRestoreContext(&frameContext, NULL);
}
HCIMPLEND
diff --git a/src/coreclr/vm/threads.cpp b/src/coreclr/vm/threads.cpp
index 6312d08b06d565..edbd6a011f33b3 100644
--- a/src/coreclr/vm/threads.cpp
+++ b/src/coreclr/vm/threads.cpp
@@ -8241,8 +8241,10 @@ void ClrRestoreNonvolatileContext(PCONTEXT ContextRecord)
{
#if defined(TARGET_WINDOWS) && defined(TARGET_AMD64)
DWORD64 ssp = GetSSP(ContextRecord);
+ __asan_handle_no_return();
ClrRestoreNonvolatileContextWorker(ContextRecord, ssp);
#else
+ __asan_handle_no_return();
// Falling back to RtlRestoreContext() for now, though it should be possible to have simpler variants for these cases
RtlRestoreContext(ContextRecord, NULL);
#endif
diff --git a/src/coreclr/vm/threadsuspend.cpp b/src/coreclr/vm/threadsuspend.cpp
index e7414425ece2d9..94b809e9f2ad40 100644
--- a/src/coreclr/vm/threadsuspend.cpp
+++ b/src/coreclr/vm/threadsuspend.cpp
@@ -2764,6 +2764,7 @@ void __stdcall Thread::RedirectedHandledJITCase(RedirectReason reason)
LOG((LF_SYNC, LL_INFO1000, "Resuming execution with RtlRestoreContext\n"));
SetLastError(dwLastError); // END_PRESERVE_LAST_ERROR
+ __asan_handle_no_return();
#ifdef TARGET_X86
g_pfnRtlRestoreContext(pCtx, NULL);
#else
@@ -3931,6 +3932,7 @@ ThrowControlForThread(
_ASSERTE(!"Should not reach here");
}
#else // FEATURE_EH_FUNCLETS
+ __asan_handle_no_return();
RtlRestoreContext(pThread->m_OSContext, NULL);
#endif // !FEATURE_EH_FUNCLETS
_ASSERTE(!"Should not reach here");
diff --git a/src/coreclr/vm/wks/CMakeLists.txt b/src/coreclr/vm/wks/CMakeLists.txt
index b0113575c1e05e..b8c5b2a3698c32 100644
--- a/src/coreclr/vm/wks/CMakeLists.txt
+++ b/src/coreclr/vm/wks/CMakeLists.txt
@@ -1,4 +1,3 @@
-
if (CLR_CMAKE_TARGET_WIN32)
if(CLR_CMAKE_HOST_ARCH_ARM OR CLR_CMAKE_HOST_ARCH_ARM64)
preprocess_files(VM_SOURCES_WKS_ARCH_ASM ${VM_SOURCES_WKS_ARCH_ASM})
diff --git a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props
index f13859dc199322..f5dc16b7677a2f 100644
--- a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props
+++ b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props
@@ -176,8 +176,10 @@
-
+
+
+
diff --git a/src/libraries/Directory.Build.targets b/src/libraries/Directory.Build.targets
index 467d900788282d..805e947626c468 100644
--- a/src/libraries/Directory.Build.targets
+++ b/src/libraries/Directory.Build.targets
@@ -128,6 +128,7 @@
+
diff --git a/src/libraries/externals.csproj b/src/libraries/externals.csproj
index c3ba982bd8e335..7f85d5d67e31fc 100644
--- a/src/libraries/externals.csproj
+++ b/src/libraries/externals.csproj
@@ -60,6 +60,12 @@
SkipUnchangedFiles="true"
UseHardlinksIfPossible="$(UseHardlink)" />
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/libraries/tests.proj b/src/libraries/tests.proj
index 5a8dd2c2aef0b1..edce0bafbf4618 100644
--- a/src/libraries/tests.proj
+++ b/src/libraries/tests.proj
@@ -513,6 +513,11 @@
Include="@(HighAOTResourceRequiringProject)" />
+
+
+
+
+
diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt
index 4ab4ece785c5c4..922df30508e20f 100644
--- a/src/mono/CMakeLists.txt
+++ b/src/mono/CMakeLists.txt
@@ -555,6 +555,12 @@ if(GCC)
set(WERROR_C "${WERROR_C} -Werror=incompatible-pointer-types")
endif()
+ # Check for sometimes suppressed warnings
+ check_c_compiler_flag(-Wreserved-identifier COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ if(COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ add_compile_definitions(COMPILER_SUPPORTS_W_RESERVED_IDENTIFIER)
+ endif()
+
if(HOST_WASI)
# When building under WASI SDK, it's stricter about discarding 'const' qualifiers, causing some existing
# code (e.g., mono-rand.c:315) to be rejected
diff --git a/src/native/corehost/CMakeLists.txt b/src/native/corehost/CMakeLists.txt
index b9674fdeb26e6e..249e4d52cf2647 100644
--- a/src/native/corehost/CMakeLists.txt
+++ b/src/native/corehost/CMakeLists.txt
@@ -30,6 +30,12 @@ add_subdirectory(dotnet)
add_subdirectory(nethost)
add_subdirectory(test)
+# If there's a dynamic ASAN runtime, then install it in the directories where we put our executables.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ install(FILES ${ASAN_RUNTIME} DESTINATION corehost)
+ install(FILES ${ASAN_RUNTIME} DESTINATION corehost_test)
+endif()
+
if (NOT RUNTIME_FLAVOR STREQUAL Mono)
if(CLR_CMAKE_TARGET_WIN32)
add_subdirectory(comhost)
diff --git a/src/native/corehost/apphost/static/CMakeLists.txt b/src/native/corehost/apphost/static/CMakeLists.txt
index 5fa066359e13a4..e1a02ece410912 100644
--- a/src/native/corehost/apphost/static/CMakeLists.txt
+++ b/src/native/corehost/apphost/static/CMakeLists.txt
@@ -259,3 +259,5 @@ target_link_libraries(
${RUNTIMEINFO_LIB}
${END_WHOLE_ARCHIVE}
)
+
+add_sanitizer_runtime_support(singlefilehost)
diff --git a/src/native/corehost/build.cmd b/src/native/corehost/build.cmd
index e43bcae3cf3cc7..89d9aa20a3d1e6 100644
--- a/src/native/corehost/build.cmd
+++ b/src/native/corehost/build.cmd
@@ -21,6 +21,7 @@ set __ConfigureOnly=0
set __IncrementalNativeBuild=0
set __Ninja=1
set __OutputRid=""
+set __ExtraCmakeParams=
:Arg_Loop
if [%1] == [] goto :InitVSEnv
@@ -49,6 +50,7 @@ if /i [%1] == [rootDir] (set __rootDir=%2&&shift&&shift&goto Arg_Loop)
if /i [%1] == [msbuild] (set __Ninja=0)
if /i [%1] == [runtimeflavor] (set __RuntimeFlavor=%2&&shift&&shift&goto Arg_Loop)
if /i [%1] == [runtimeconfiguration] (set __RuntimeConfiguration=%2&&shift&&shift&goto Arg_Loop)
+if /i [%1] == [-fsanitize] ( set __ExtraCmakeParams=%__ExtraCmakeParams% "-DCLR_CMAKE_ENABLE_SANITIZERS=%2"&&shift&&shift&goto Arg_Loop)
shift
goto :Arg_Loop
diff --git a/src/native/corehost/corehost.proj b/src/native/corehost/corehost.proj
index 18ac25f41841d2..9cdbfa0e434aa0 100644
--- a/src/native/corehost/corehost.proj
+++ b/src/native/corehost/corehost.proj
@@ -81,6 +81,7 @@
$(BuildArgs) -cmakeargs "$(CMakeArgs)"
$(BuildArgs) -ninja
$(BuildArgs) -runtimeflavor $(RuntimeFlavor)
+ $(BuildArgs) -fsanitize=$(EnableNativeSanitizers)
$(BuildArgs) /p:OfficialBuildId="$(OfficialBuildId)"
$(BuildArgs) -outputrid $(OutputRID)
@@ -141,6 +142,7 @@
$(BuildArgs) msbuild
$(BuildArgs) runtimeflavor $(RuntimeFlavor)
$(BuildArgs) runtimeconfiguration $(RuntimeConfiguration)
+ $(BuildArgs) -fsanitize=$(EnableNativeSanitizers)
+
+
+
+
+
+
+
+
-
+
-
+
-
+
-
+
True
-
+
-
+
True
-
+
True
-
+
@@ -93,26 +108,26 @@
Condition="'%(RuntimeArtifactsIncludeFolders.IncludeSubFolders)' != 'True'"
Include="$(CoreCLRArtifactsPath)%(RunTimeArtifactsIncludeFolders.Identity)*"
Exclude="@(RunTimeArtifactsExcludeFiles -> '$(CoreCLRArtifactsPath)%(Identity)')"
- TargetDir="%(RunTimeArtifactsIncludeFolders.Identity)" />
+ TargetDir="%(RunTimeArtifactsIncludeFolders.TargetDir)" />
+ TargetDir="%(RunTimeArtifactsIncludeFolders.TargetDir)" />
- $(CoreCLRArtifactsPath)x64/crossgen2
+ $(CoreCLRArtifactsPath)x64/crossgen2
diff --git a/src/tests/Common/helixpublishwitharcade.proj b/src/tests/Common/helixpublishwitharcade.proj
index edc43366cd9e99..db4ce658d6c767 100644
--- a/src/tests/Common/helixpublishwitharcade.proj
+++ b/src/tests/Common/helixpublishwitharcade.proj
@@ -677,6 +677,7 @@
+
diff --git a/src/tests/Common/publishdependency.targets b/src/tests/Common/publishdependency.targets
index 4a16052008d7d2..eff6edb3a1144c 100644
--- a/src/tests/Common/publishdependency.targets
+++ b/src/tests/Common/publishdependency.targets
@@ -28,7 +28,7 @@
+ Properties="Language=C#;RuntimeIdentifier=$(OutputRID);CORE_ROOT=$(CORE_ROOT);EnableNativeSanitizers=$(EnableNativeSanitizers)" />
diff --git a/src/tests/Directory.Build.props b/src/tests/Directory.Build.props
index 4574f6cdb1501c..90d5d9d17a2a70 100644
--- a/src/tests/Directory.Build.props
+++ b/src/tests/Directory.Build.props
@@ -19,6 +19,7 @@
$(__AltJitArch)
+ $(__EnableNativeSanitizers)
diff --git a/src/tests/Directory.Build.targets b/src/tests/Directory.Build.targets
index b5bec81d6845e9..fe922918c11ec1 100644
--- a/src/tests/Directory.Build.targets
+++ b/src/tests/Directory.Build.targets
@@ -99,6 +99,7 @@
<_WillCLRTestProjectBuild Condition="'$(DisableProjectBuild)' == 'true'">false
<_WillCLRTestProjectBuild Condition="'$(NativeAotIncompatible)' == 'true' and '$(TestBuildMode)' == 'nativeaot'">false
<_WillCLRTestProjectBuild Condition="'$(RuntimeFlavor)' == 'mono' And '$(AlwaysUseCrossgen2)' == 'true'">false
+ <_WillCLRTestProjectBuild Condition="'$(EnableNativeSanitizers)' != '' And '$(AlwaysUseCrossgen2)' == 'true'">false
<_CopyNativeProjectBinaries Condition="'$(__CopyNativeTestBinaries)' != '1'">$(__CopyNativeProjectsAfterCombinedTestBuild)
@@ -530,7 +531,7 @@
partial
$(CoreCLRILCompilerDir)
- $(CoreCLRCrossILCompilerDir)
+ $(CoreCLRCrossILCompilerDir)
$(CoreCLRILCompilerDir)netstandard/ILCompiler.Build.Tasks.dll
$(CoreCLRAotSdkDir)
$(MicrosoftNetCoreAppRuntimePackRidLibTfmDir)
@@ -564,8 +565,14 @@
+
+
+
+
+
+
diff --git a/src/tests/Interop/COM/NativeClients/DefaultInterfaces/CMakeLists.txt b/src/tests/Interop/COM/NativeClients/DefaultInterfaces/CMakeLists.txt
index 8338be8220d4e0..b58d8b34a28475 100644
--- a/src/tests/Interop/COM/NativeClients/DefaultInterfaces/CMakeLists.txt
+++ b/src/tests/Interop/COM/NativeClients/DefaultInterfaces/CMakeLists.txt
@@ -16,3 +16,7 @@ file(GENERATE OUTPUT $/CoreShim.X.manifest INPU
# add the install targets
install (TARGETS COMClientDefaultInterfaces DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/Interop/COM/NativeClients/Dispatch/CMakeLists.txt b/src/tests/Interop/COM/NativeClients/Dispatch/CMakeLists.txt
index a3e35c353582f2..6412f97931e455 100644
--- a/src/tests/Interop/COM/NativeClients/Dispatch/CMakeLists.txt
+++ b/src/tests/Interop/COM/NativeClients/Dispatch/CMakeLists.txt
@@ -15,3 +15,7 @@ file(GENERATE OUTPUT $/CoreShim.X.manifest IN
# add the install targets
install (TARGETS COMClientDispatch DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/Interop/COM/NativeClients/Events/CMakeLists.txt b/src/tests/Interop/COM/NativeClients/Events/CMakeLists.txt
index 1443b6203727de..af9e12d0f35a9a 100644
--- a/src/tests/Interop/COM/NativeClients/Events/CMakeLists.txt
+++ b/src/tests/Interop/COM/NativeClients/Events/CMakeLists.txt
@@ -16,3 +16,7 @@ file(GENERATE OUTPUT $/CoreShim.X.manifest INPU
# add the install targets
install (TARGETS COMClientEvents DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/Interop/COM/NativeClients/Licensing/CMakeLists.txt b/src/tests/Interop/COM/NativeClients/Licensing/CMakeLists.txt
index ac9640e230f336..014a7824b3db5d 100644
--- a/src/tests/Interop/COM/NativeClients/Licensing/CMakeLists.txt
+++ b/src/tests/Interop/COM/NativeClients/Licensing/CMakeLists.txt
@@ -16,3 +16,7 @@ file(GENERATE OUTPUT $/CoreShim.X.manifest INPU
# add the install targets
install (TARGETS COMClientLicensing DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/Interop/COM/NativeClients/Primitives/CMakeLists.txt b/src/tests/Interop/COM/NativeClients/Primitives/CMakeLists.txt
index 0fcfe6dcce98d3..096453469ffde5 100644
--- a/src/tests/Interop/COM/NativeClients/Primitives/CMakeLists.txt
+++ b/src/tests/Interop/COM/NativeClients/Primitives/CMakeLists.txt
@@ -21,3 +21,7 @@ file(GENERATE OUTPUT $/CoreShim.X.manifest INPU
# add the install targets
install (TARGETS COMClientPrimitives DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/build.cmd b/src/tests/build.cmd
index 7e70fa991dc1a1..6e1b8f684d9f42 100644
--- a/src/tests/build.cmd
+++ b/src/tests/build.cmd
@@ -57,6 +57,7 @@ set __SkipGenerateLayout=0
set __GenerateLayoutOnly=0
set __Ninja=1
set __CMakeArgs=
+set __EnableNativeSanitizers=
set __Priority=0
set __BuildNeedTargetArg=
@@ -121,6 +122,7 @@ if /i "%arg%" == "tree" (set __BuildTestTree=!__BuildTestTree!%
if /i "%arg%" == "log" (set __BuildLogRootName=%2&set processedArgs=!processedArgs! %1 %2&shift&shift&goto Arg_Loop)
if /i "%arg%" == "exclude" (set __Exclude=%2&set processedArgs=!processedArgs! %1 %2&shift&shift&goto Arg_Loop)
if /i "%arg%" == "priority" (set __Priority=%2&set processedArgs=!processedArgs! %1 %2&shift&shift&goto Arg_Loop)
+if /i "%arg%" == "fsanitize" (set __CMakeArgs=%__CMakeArgs% "-DCLR_CMAKE_ENABLE_SANITIZERS=%2"&set __EnableNativeSanitizers=%2&set processedArgs=!processedArgs! %1=%2&shift&shift&goto Arg_Loop)
@REM The following arguments also consume two subsequent arguments
if /i "%arg%" == "CMakeArgs" (set __CMakeArgs="%2=%3" %__CMakeArgs%&set "processedArgs=!processedArgs! %1 %2 %3"&shift&shift&shift&goto Arg_Loop)
@@ -175,6 +177,7 @@ if defined __TestArgParsing (
echo.__Ninja=%__Ninja%
echo.__CMakeArgs=%__CMakeArgs%
echo.__Priority=%__Priority%
+ echo.__EnableNativeSanitizers=%__EnableNativeSanitizers%
echo.
)
@@ -405,6 +408,7 @@ echo -Log ^: Base file name to use for log files (used in lab pipelines th
echo.
echo -CMakeArgs ^=^: Specify argument values to pass directly to CMake.
echo Can be used multiple times to provide multiple CMake arguments.
+echo -fsanitize ^: Build the native test components with the specified native sanitizers.
echo.
echo -- : All arguments following this tag will be passed directly to MSBuild.
echo. Any unrecognized arguments will also be passed directly to MSBuild.
diff --git a/src/tests/build.sh b/src/tests/build.sh
index 50efe6a764ebbf..f222c69988c788 100755
--- a/src/tests/build.sh
+++ b/src/tests/build.sh
@@ -61,7 +61,7 @@ build_Tests()
if [[ "$__SkipNative" != 1 && "$__BuildTestWrappersOnly" != 1 && "$__GenerateLayoutOnly" != 1 && "$__CopyNativeTestBinaries" != 1 && \
"$__TargetOS" != "browser" && "$__TargetOS" != "wasi" && "$__TargetOS" != "android" && "$__TargetOS" != "ios" && "$__TargetOS" != "iossimulator" && "$__TargetOS" != "tvos" && "$__TargetOS" != "tvossimulator" ]]; then
- build_native "$__TargetOS" "$__TargetArch" "$__TestDir" "$__NativeTestIntermediatesDir" "install" "CoreCLR test component"
+ build_native "$__TargetOS" "$__TargetArch" "$__TestDir" "$__NativeTestIntermediatesDir" "install" "$__CMakeArgs" "CoreCLR test component"
if [[ "$?" -ne 0 ]]; then
echo "${__ErrMsgPrefix}${__MsgPrefix}Error: native test build failed. Refer to the build log files for details (above)"
@@ -110,6 +110,7 @@ build_Tests()
export __MsgPrefix
export __ErrMsgPrefix
export __Exclude
+ export EnableNativeSanitizers
# Generate build command
buildArgs=("$__RepoRootDir/src/tests/build.proj")
@@ -363,6 +364,7 @@ __MonoAot=0
__MonoFullAot=0
__BuildLogRootName="TestBuild"
CORE_ROOT=
+EnableNativeSanitizers=
source $__RepoRootDir/src/coreclr/_build-commons.sh
diff --git a/src/tests/nativeaot/CustomMain/CustomMainNative.cpp b/src/tests/nativeaot/CustomMain/CustomMainNative.cpp
index 590051f6c5e7f2..e9bb1c25b9d460 100644
--- a/src/tests/nativeaot/CustomMain/CustomMainNative.cpp
+++ b/src/tests/nativeaot/CustomMain/CustomMainNative.cpp
@@ -4,6 +4,10 @@
#include
#include
+#ifndef TARGET_WINDOWS
+#define __stdcall
+#endif
+
#if defined(_WIN32)
extern "C" int __managed__Main(int argc, wchar_t* argv[]);
#else
@@ -22,3 +26,10 @@ int main(int argc, char* argv[])
IncrementExitCode(61);
return __managed__Main(argc, argv);
}
+
+extern "C" const char* __stdcall __asan_default_options()
+{
+ // NativeAOT is not designed to be unloadable, so we'll leak a few allocations from the shared library.
+ // Disable leak detection as we don't care about these leaks as of now.
+ return "detect_leaks=0 use_sigaltstack=0";
+}
diff --git a/src/tests/nativeaot/GenerateUnmanagedEntryPoints/GenerateUnmanagedEntryPoints.csproj b/src/tests/nativeaot/GenerateUnmanagedEntryPoints/GenerateUnmanagedEntryPoints.csproj
index db5f0741f8d419..e2a1107993f8a5 100644
--- a/src/tests/nativeaot/GenerateUnmanagedEntryPoints/GenerateUnmanagedEntryPoints.csproj
+++ b/src/tests/nativeaot/GenerateUnmanagedEntryPoints/GenerateUnmanagedEntryPoints.csproj
@@ -4,6 +4,11 @@
BuildAndRun
true
true
+
+ true
diff --git a/src/tests/nativeaot/SmokeTests/DwarfDump/DwarfDump.csproj b/src/tests/nativeaot/SmokeTests/DwarfDump/DwarfDump.csproj
index 25eece838c4b43..b0645183024ecd 100644
--- a/src/tests/nativeaot/SmokeTests/DwarfDump/DwarfDump.csproj
+++ b/src/tests/nativeaot/SmokeTests/DwarfDump/DwarfDump.csproj
@@ -6,6 +6,8 @@
0
true
+
+ true
false
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx.csproj
index 3cf9043e062dff..63f975aee907cb 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);AVX_INTRINSICS;VECTORT128_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx2.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx2.csproj
index 626f88edc7278d..334d899e8ea51c 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx2.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx2.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);AVX2_INTRINSICS;VECTORT256_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx512.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx512.csproj
index 24da060cc6622c..2f045ae5a40713 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx512.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx512.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);AVX512_INTRINSICS;VECTORT256_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx_NoAvx2.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx_NoAvx2.csproj
index 9565259240f01f..649e14453532c1 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx_NoAvx2.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Avx_NoAvx2.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);AVX_INTRINSICS;VECTORT128_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Baseline.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Baseline.csproj
index 9e5d0c79e268e1..6da7c0da48559b 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Baseline.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Baseline.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);BASELINE_INTRINSICS;VECTORT128_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Sse42.csproj b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Sse42.csproj
index bf1a725b11a44d..c2922e1883f450 100644
--- a/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Sse42.csproj
+++ b/src/tests/nativeaot/SmokeTests/HardwareIntrinsics/X64Sse42.csproj
@@ -4,6 +4,8 @@
BuildAndRun
0
true
+
+ true
true
$(DefineConstants);SSE42_INTRINSICS;VECTORT128_INTRINSICS
diff --git a/src/tests/nativeaot/SmokeTests/SharedLibrary/CMakeLists.txt b/src/tests/nativeaot/SmokeTests/SharedLibrary/CMakeLists.txt
index 5af70a164ba562..82893d7af32a02 100644
--- a/src/tests/nativeaot/SmokeTests/SharedLibrary/CMakeLists.txt
+++ b/src/tests/nativeaot/SmokeTests/SharedLibrary/CMakeLists.txt
@@ -8,4 +8,8 @@ if (CLR_CMAKE_TARGET_UNIX)
endif()
# add the install targets
-install (TARGETS PInvokeNative DESTINATION bin)
+install (TARGETS SharedLibraryDriver DESTINATION bin)
+# If there's a dynamic ASAN runtime, then copy it to project output.
+if (NOT "${ASAN_RUNTIME}" STREQUAL "")
+ file(COPY "${ASAN_RUNTIME}" DESTINATION "${CMAKE_CURRENT_BINARY_DIR}")
+endif()
diff --git a/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.cpp b/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.cpp
index 331011165d54cd..c76b3535b03023 100644
--- a/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.cpp
+++ b/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.cpp
@@ -82,3 +82,10 @@ int main(int argc, char* argv[])
return 100;
}
+
+extern "C" const char* __stdcall __asan_default_options()
+{
+ // NativeAOT is not designed to be unloadable, so we'll leak a few allocations from the shared library.
+ // Disable leak detection as we don't care about these leaks as of now.
+ return "detect_leaks=0 use_sigaltstack=0";
+}
diff --git a/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.csproj b/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.csproj
index 09b36ffbd9fb73..aadb18279ffdf7 100644
--- a/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.csproj
+++ b/src/tests/nativeaot/SmokeTests/SharedLibrary/SharedLibrary.csproj
@@ -11,12 +11,14 @@
nul
+copy /y clang_rt.* native\
copy /y SharedLibraryDriver.exe native\SharedLibrary.exe
]]>
diff --git a/src/tests/readytorun/coreroot_determinism/coreroot_determinism.csproj b/src/tests/readytorun/coreroot_determinism/coreroot_determinism.csproj
index 5838f8fa813689..5f651694cc1c92 100644
--- a/src/tests/readytorun/coreroot_determinism/coreroot_determinism.csproj
+++ b/src/tests/readytorun/coreroot_determinism/coreroot_determinism.csproj
@@ -6,6 +6,8 @@
true
false
+
+ true
2.0
diff --git a/src/tests/readytorun/determinism/crossgen2determinism.csproj b/src/tests/readytorun/determinism/crossgen2determinism.csproj
index c0219b2b48594d..8544d11bd5257f 100644
--- a/src/tests/readytorun/determinism/crossgen2determinism.csproj
+++ b/src/tests/readytorun/determinism/crossgen2determinism.csproj
@@ -2,6 +2,8 @@
exe
true
+
+ true
true
diff --git a/src/tests/readytorun/multifolder/multifolder.csproj b/src/tests/readytorun/multifolder/multifolder.csproj
index 67e75c04322cba..0e1410f50bac06 100644
--- a/src/tests/readytorun/multifolder/multifolder.csproj
+++ b/src/tests/readytorun/multifolder/multifolder.csproj
@@ -7,6 +7,8 @@
true
+
+ true
false