[hwasan] support hwasan-match-all-tag flag for hwasan meminstrinsic calls

This patch implements `__hwasan_memset_match_all`, `__hwasan_memcpy_match_all` and `__hwasan_memmove_match_all`, making hwasan-match-all-tag flag working for hwasan versions of memset, memcpy and memmove.

Reviewed By: vitalybuka

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

GitOrigin-RevId: ba13e1b4381e87f80837f8215309af56a0da2c9c
diff --git a/lib/hwasan/hwasan_interface_internal.h b/lib/hwasan/hwasan_interface_internal.h
index 48ff3d5..e7804cc 100644
--- a/lib/hwasan/hwasan_interface_internal.h
+++ b/lib/hwasan/hwasan_interface_internal.h
@@ -236,6 +236,13 @@
 void *__hwasan_memmove(void *dest, const void *src, uptr n);
 
 SANITIZER_INTERFACE_ATTRIBUTE
+void *__hwasan_memcpy_match_all(void *dst, const void *src, uptr size, u8);
+SANITIZER_INTERFACE_ATTRIBUTE
+void *__hwasan_memset_match_all(void *s, int c, uptr n, u8);
+SANITIZER_INTERFACE_ATTRIBUTE
+void *__hwasan_memmove_match_all(void *dest, const void *src, uptr n, u8);
+
+SANITIZER_INTERFACE_ATTRIBUTE
 void __hwasan_set_error_report_callback(void (*callback)(const char *));
 }  // extern "C"
 
diff --git a/lib/hwasan/hwasan_memintrinsics.cpp b/lib/hwasan/hwasan_memintrinsics.cpp
index ea7f5ce..16d6f90 100644
--- a/lib/hwasan/hwasan_memintrinsics.cpp
+++ b/lib/hwasan/hwasan_memintrinsics.cpp
@@ -42,3 +42,33 @@
       reinterpret_cast<uptr>(from), size);
   return memmove(to, from, size);
 }
+
+void *__hwasan_memset_match_all(void *block, int c, uptr size,
+                                u8 match_all_tag) {
+  if (GetTagFromPointer(reinterpret_cast<uptr>(block)) != match_all_tag)
+    CheckAddressSized<ErrorAction::Recover, AccessType::Store>(
+        reinterpret_cast<uptr>(block), size);
+  return memset(block, c, size);
+}
+
+void *__hwasan_memcpy_match_all(void *to, const void *from, uptr size,
+                                u8 match_all_tag) {
+  if (GetTagFromPointer(reinterpret_cast<uptr>(to)) != match_all_tag)
+    CheckAddressSized<ErrorAction::Recover, AccessType::Store>(
+        reinterpret_cast<uptr>(to), size);
+  if (GetTagFromPointer(reinterpret_cast<uptr>(from)) != match_all_tag)
+    CheckAddressSized<ErrorAction::Recover, AccessType::Load>(
+        reinterpret_cast<uptr>(from), size);
+  return memcpy(to, from, size);
+}
+
+void *__hwasan_memmove_match_all(void *to, const void *from, uptr size,
+                                 u8 match_all_tag) {
+  if (GetTagFromPointer(reinterpret_cast<uptr>(to)) != match_all_tag)
+    CheckAddressSized<ErrorAction::Recover, AccessType::Store>(
+        reinterpret_cast<uptr>(to), size);
+  if (GetTagFromPointer(reinterpret_cast<uptr>(from)) != match_all_tag)
+    CheckAddressSized<ErrorAction::Recover, AccessType::Load>(
+        reinterpret_cast<uptr>(from), size);
+  return memmove(to, from, size);
+}