[PATCH] D23046: [asan] Intercept RtlRaiseException instead of kernel32!RaiseException

Reid Kleckner via llvm-commits llvm-commits at lists.llvm.org
Mon Aug 1 18:46:19 PDT 2016


rnk created this revision.
rnk added a reviewer: etienneb.
rnk added a subscriber: llvm-commits.
Herald added a subscriber: kubabrecka.

On my install of Windows 10, RaiseException is a tail call to
kernelbase!RaiseException. Obviously, we fail to intercept that.
Instead, try hooking at the ntdll!RtlRaiseException layer. It is
unlikely that this layer will contain control flow.

Intercepting at this level requires adding a decoding for
'LEA ESP, [ESP + 0xXXXXXXXX]', which is a really obscure way to write
'SUB ESP, 0xXXXXXXXX' that avoids clobbering EFLAGS.

https://reviews.llvm.org/D23046

Files:
  lib/asan/asan_win.cc
  lib/interception/interception_win.cc
  lib/interception/tests/interception_win_test.cc

Index: lib/interception/tests/interception_win_test.cc
===================================================================
--- lib/interception/tests/interception_win_test.cc
+++ lib/interception/tests/interception_win_test.cc
@@ -163,6 +163,13 @@
     0x90, 0x90, 0x90, 0x90,
 };
 
+const u8 kPatchableCode5[] = {
+    0x55,                                      // push    ebp
+    0x8b, 0xec,                                // mov     ebp,esp
+    0x8d, 0xa4, 0x24, 0x30, 0xfd, 0xff, 0xff,  // lea     esp,[esp-2D0h]
+    0x54,                                      // push    esp
+};
+
 const u8 kUnpatchableCode1[] = {
     0xC3,                           // ret
 };
@@ -474,6 +481,7 @@
   EXPECT_TRUE(TestFunctionPatching(kPatchableCode3, override));
 #endif
   EXPECT_TRUE(TestFunctionPatching(kPatchableCode4, override));
+  EXPECT_TRUE(TestFunctionPatching(kPatchableCode5, override));
 
   EXPECT_FALSE(TestFunctionPatching(kUnpatchableCode1, override));
   EXPECT_FALSE(TestFunctionPatching(kUnpatchableCode2, override));
Index: lib/interception/interception_win.cc
===================================================================
--- lib/interception/interception_win.cc
+++ lib/interception/interception_win.cc
@@ -565,6 +565,9 @@
     case 0x24748B:  // 8B 74 24 XX : mov esi, dword ptr [esp + XX]
     case 0x247C8B:  // 8B 7C 24 XX : mov edi, dword ptr [esp + XX]
       return 4;
+
+    case 0x24A48D:  // 8D A4 24 XX XX XX XX : lea esp, [esp + XX XX XX XX]
+      return 7;
   }
 
   switch (*(u32*)address) {
Index: lib/asan/asan_win.cc
===================================================================
--- lib/asan/asan_win.cc
+++ lib/asan/asan_win.cc
@@ -71,10 +71,10 @@
 }  // extern "C"
 
 // ---------------------- Windows-specific interceptors ---------------- {{{
-INTERCEPTOR_WINAPI(void, RaiseException, void *a, void *b, void *c, void *d) {
-  CHECK(REAL(RaiseException));
+INTERCEPTOR_WINAPI(void, RtlRaiseException, void *ExceptionRecord) {
+  CHECK(REAL(RtlRaiseException));
   __asan_handle_no_return();
-  REAL(RaiseException)(a, b, c, d);
+  REAL(RtlRaiseException)(ExceptionRecord);
 }
 
 
@@ -166,7 +166,10 @@
 
 void InitializePlatformInterceptors() {
   ASAN_INTERCEPT_FUNC(CreateThread);
-  ASAN_INTERCEPT_FUNC(RaiseException);
+  // RtlRaiseException is always linked dynamically.
+  CHECK(::__interception::OverrideFunction("RtlRaiseException",
+                                           (uptr)WRAP(RtlRaiseException),
+                                           (uptr *)&REAL(RtlRaiseException)));
 
 #ifdef _WIN64
   ASAN_INTERCEPT_FUNC(__C_specific_handler);


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D23046.66416.patch
Type: text/x-patch
Size: 2608 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20160802/3c616182/attachment.bin>


More information about the llvm-commits mailing list