Merge "Fix bionic unit tests with HWASan after Fortify+HWASan workaround." into main
diff --git a/tests/Android.bp b/tests/Android.bp
index 4509cc4..d779400 100644
--- a/tests/Android.bp
+++ b/tests/Android.bp
@@ -649,6 +649,9 @@
     name: "bionic_fortify_tests_defaults",
     cflags: [
         "-U_FORTIFY_SOURCE",
+        // Without this, HWASan will not recognize (i.e. will not detect errors involving)
+        // calls to mem* functions.
+        "-fbuiltin",
     ],
     srcs: ["fortify_test_main.cpp"],
     static_libs: [
@@ -716,6 +719,9 @@
     ],
     cflags: [
         "-U_FORTIFY_SOURCE",
+        // Without this, HWASan will not recognize (i.e. will not detect errors involving)
+        // calls to mem* functions.
+        "-fbuiltin",
     ],
     srcs: ["clang_fortify_tests.cpp"],
 }
diff --git a/tests/clang_fortify_tests.cpp b/tests/clang_fortify_tests.cpp
index da7926d..7922f0a 100644
--- a/tests/clang_fortify_tests.cpp
+++ b/tests/clang_fortify_tests.cpp
@@ -125,6 +125,12 @@
 #define EXPECT_FORTIFY_DEATH_STRUCT EXPECT_NO_DEATH
 #endif
 
+#if __has_feature(hwaddress_sanitizer)
+#define EXPECT_FORTIFY_OR_HWASAN_DEATH(expr) DIE_WITH(expr, testing::KilledBySignal(SIGABRT), "HWAddressSanitizer")
+#else
+#define EXPECT_FORTIFY_OR_HWASAN_DEATH EXPECT_FORTIFY_DEATH
+#endif
+
 #define FORTIFY_TEST(test_name) TEST_F(FORTIFY_TEST_NAME, test_name)
 
 #else  // defined(COMPILATION_TESTS)
@@ -132,6 +138,7 @@
 #define EXPECT_NO_DEATH(expr) expr
 #define EXPECT_FORTIFY_DEATH(expr) expr
 #define EXPECT_FORTIFY_DEATH_STRUCT EXPECT_FORTIFY_DEATH
+#define EXPECT_FORTIFY_OR_HWASAN_DEATH EXPECT_FORTIFY_DEATH
 #define FORTIFY_TEST(test_name) void test_name()
 #endif
 
@@ -161,15 +168,15 @@
   {
     char large_buffer[sizeof(small_buffer) + 1] = {};
     // expected-error@+1{{will always overflow}}
-    EXPECT_FORTIFY_DEATH(memcpy(small_buffer, large_buffer, sizeof(large_buffer)));
+    EXPECT_FORTIFY_OR_HWASAN_DEATH(memcpy(small_buffer, large_buffer, sizeof(large_buffer)));
     // expected-error@+1{{will always overflow}}
-    EXPECT_FORTIFY_DEATH(memmove(small_buffer, large_buffer, sizeof(large_buffer)));
+    EXPECT_FORTIFY_OR_HWASAN_DEATH(memmove(small_buffer, large_buffer, sizeof(large_buffer)));
     // FIXME(gbiv): look into removing mempcpy's diagnose_if bits once the b/149839606 roll sticks.
     // expected-error@+2{{will always overflow}}
     // expected-error@+1{{size bigger than buffer}}
     EXPECT_FORTIFY_DEATH(mempcpy(small_buffer, large_buffer, sizeof(large_buffer)));
     // expected-error@+1{{will always overflow}}
-    EXPECT_FORTIFY_DEATH(memset(small_buffer, 0, sizeof(large_buffer)));
+    EXPECT_FORTIFY_OR_HWASAN_DEATH(memset(small_buffer, 0, sizeof(large_buffer)));
     // expected-warning@+1{{arguments got flipped?}}
     EXPECT_NO_DEATH(memset(small_buffer, sizeof(small_buffer), 0));
     // expected-error@+1{{size bigger than buffer}}
diff --git a/tests/fortify_test.cpp b/tests/fortify_test.cpp
index fd1680b..7e1ae48 100644
--- a/tests/fortify_test.cpp
+++ b/tests/fortify_test.cpp
@@ -29,12 +29,20 @@
 
 #include <android-base/silent_death_test.h>
 
+#include "DoNotOptimize.h"
+
 #if defined(__BIONIC__)
 #define ASSERT_FORTIFY(expr) ASSERT_EXIT(expr, testing::KilledBySignal(SIGABRT), "FORTIFY")
 #else
 #define ASSERT_FORTIFY(expr) ASSERT_EXIT(expr, testing::KilledBySignal(SIGABRT), "")
 #endif
 
+#if __has_feature(hwaddress_sanitizer)
+#define ASSERT_FORTIFY_OR_HWASAN(expr) ASSERT_EXIT(expr, testing::KilledBySignal(SIGABRT), "HWAddressSanitizer")
+#else
+#define ASSERT_FORTIFY_OR_HWASAN ASSERT_FORTIFY
+#endif
+
 // Fortify test code needs to run multiple times, so TEST_NAME macro is used to
 // distinguish different tests. TEST_NAME is defined in compilation command.
 #define DEATHTEST_PASTER(name) name##_DeathTest
@@ -415,8 +423,13 @@
 }
 
 TEST_F(DEATHTEST, sprintf2_fortified) {
+  // glibc's fortified implementation of sprintf is smart enough to be able to detect this bug at
+  // compile time, but we want to check if it can also be detected at runtime.
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-overflow"
   char buf[5];
   ASSERT_FORTIFY(sprintf(buf, "aaaaa"));
+#pragma clang diagnostic pop
 }
 
 static int vsprintf_helper(const char* fmt, ...) {
@@ -480,7 +493,7 @@
   char buf[20];
   strcpy(buf, "0123456789");
   volatile size_t n = 10;
-  ASSERT_FORTIFY(memmove(buf + 11, buf, n));
+  ASSERT_FORTIFY_OR_HWASAN(DoNotOptimize(memmove(buf + 11, buf, n)));
 }
 
 TEST_F(DEATHTEST, memcpy_fortified) {
@@ -488,13 +501,13 @@
   char bufb[10];
   strcpy(bufa, "012345678");
   volatile size_t n = 11;
-  ASSERT_FORTIFY(memcpy(bufb, bufa, n));
+  ASSERT_FORTIFY_OR_HWASAN(DoNotOptimize(memcpy(bufb, bufa, n)));
 }
 
 TEST_F(DEATHTEST, memset_fortified) {
   char buf[10];
   volatile size_t n = 11;
-  ASSERT_FORTIFY(memset(buf, 0, n));
+  ASSERT_FORTIFY_OR_HWASAN(DoNotOptimize(memset(buf, 0, n)));
 }
 
 TEST_F(DEATHTEST, stpncpy_fortified) {