Bug 653361 - Dll Block list doesn't work when Avast! Anti-Virus is installed. r=vlad
authorMakoto Kato <m_kato@ga2.so-net.ne.jp>
Sat, 20 Aug 2011 00:34:28 +0900
changeset 75564 be9c15f7dd336427a760a05a0d292f6b6646ba92
parent 75563 33000157292b4cef2533a8769a49cd7d1e86d64d
child 75565 241af714f92df2d108448975263213c9ae3699a0
push id3
push userfelipc@gmail.com
push dateFri, 30 Sep 2011 20:09:13 +0000
reviewersvlad
bugs653361
milestone9.0a1
Bug 653361 - Dll Block list doesn't work when Avast! Anti-Virus is installed. r=vlad
toolkit/xre/nsWindowsDllInterceptor.h
--- a/toolkit/xre/nsWindowsDllInterceptor.h
+++ b/toolkit/xre/nsWindowsDllInterceptor.h
@@ -184,16 +184,17 @@ protected:
     byteptr_t tramp = FindTrampolineSpace();
     if (!tramp)
       return 0;
 
     byteptr_t origBytes = (byteptr_t) origFunction;
 
     int nBytes = 0;
 #if defined(_M_IX86)
+    int nJmp32 = -1;
     while (nBytes < 5) {
       // Understand some simple instructions that might be found in a
       // prologue; we might need to extend this as necessary.
       //
       // Note!  If we ever need to understand jump instructions, we'll
       // need to rewrite the displacement argument.
       if (origBytes[nBytes] >= 0x88 && origBytes[nBytes] <= 0x8B) {
         // various MOVs; but only handle the case where it truly is a 2-byte instruction
@@ -211,16 +212,21 @@ protected:
         // PUSH with 4-byte operand
         nBytes += 5;
       } else if ((origBytes[nBytes] & 0xf0) == 0x50) {
         // 1-byte PUSH/POP
         nBytes++;
       } else if (origBytes[nBytes] == 0x6A) {
         // PUSH imm8
         nBytes += 2;
+      } else if (origBytes[nBytes] == 0xe9) {
+        // JMP rel32
+        nJmp32 = nBytes;
+        // jmp 32bit offset
+        nBytes += 5;
       } else {
         //printf ("Unknown x86 instruction byte 0x%02x, aborting trampoline\n", origBytes[nBytes]);
         return 0;
       }
     }
 #elif defined(_M_X64)
     int pJmp32 = -1;
 
@@ -344,18 +350,26 @@ protected:
     tramp += sizeof(void *);
 
     memcpy(tramp, origFunction, nBytes);
 
     // OrigFunction+N, the target of the trampoline
     byteptr_t trampDest = origBytes + nBytes;
 
 #if defined(_M_IX86)
-    tramp[nBytes] = 0xE9; // jmp
-    *((intptr_t*)(tramp+nBytes+1)) = (intptr_t)trampDest - (intptr_t)(tramp+nBytes+5); // target displacement
+    if (nJmp32 >= 0) {
+      // Function entry has JMP rel32.  We replace with correct target address.
+      byteptr_t targetAddress =
+        origBytes + nJmp32 + 5 + (*((LONG*)(origBytes+nJmp32+1)));
+      *((intptr_t*)(tramp+nJmp32+1)) =
+        (intptr_t)targetAddress - (intptr_t)(tramp+nJmp32+5);
+    } else {
+      tramp[nBytes] = 0xE9; // jmp
+      *((intptr_t*)(tramp+nBytes+1)) = (intptr_t)trampDest - (intptr_t)(tramp+nBytes+5); // target displacement
+    }
 #elif defined(_M_X64)
     // If JMP32 opcode found, we don't insert to trampoline jump 
     if (pJmp32 >= 0) {
       // convert JMP 32bit offset to JMP 64bit direct
       byteptr_t directJmpAddr = origBytes + pJmp32 + 5 + (*((LONG*)(origBytes+pJmp32+1)));
       // mov r11, address
       tramp[pJmp32]   = 0x49;
       tramp[pJmp32+1] = 0xbb;