call+jmp trick filter: add Jxx with 32-bit displacement

src/fcto_ml.ch src/fcto_ml2.ch src/stub/macros.ash

committer: jreiser <jreiser> 977078022 +0000
This commit is contained in:
John Reiser
2000-12-17 18:33:42 +00:00
parent 118660205e
commit f275b12837
3 changed files with 29 additions and 18 deletions
+5 -3
View File
@@ -66,7 +66,7 @@
// //
**************************************************************************/ **************************************************************************/
#define COND(b,x) (b[x] == 0xe8) #define COND(b,x,lastcall) (b[x] == 0xe8)
#define F f_cto32_e8_bswap_le #define F f_cto32_e8_bswap_le
#define U u_cto32_e8_bswap_le #define U u_cto32_e8_bswap_le
#include "fcto_ml2.ch" #include "fcto_ml2.ch"
@@ -77,7 +77,7 @@
#undef F #undef F
#undef COND #undef COND
#define COND(b,x) (b[x] == 0xe9) #define COND(b,x,lastcall) (b[x] == 0xe9)
#define F f_cto32_e9_bswap_le #define F f_cto32_e9_bswap_le
#define U u_cto32_e9_bswap_le #define U u_cto32_e9_bswap_le
#include "fcto_ml2.ch" #include "fcto_ml2.ch"
@@ -88,7 +88,9 @@
#undef F #undef F
#undef COND #undef COND
#define COND(b,x) (b[x] == 0xe8 || b[x] == 0xe9) #define COND(b,x,lastcall) (b[x] == 0xe8 || b[x] == 0xe9 \
|| (lastcall!=(x) && 0xf==b[(x)-1] \
&& 0x80<=b[x] && b[x]<=0x8f) )
#define F f_cto32_e8e9_bswap_le #define F f_cto32_e8e9_bswap_le
#define U u_cto32_e8e9_bswap_le #define U u_cto32_e8e9_bswap_le
#include "fcto_ml2.ch" #include "fcto_ml2.ch"
+11 -10
View File
@@ -43,8 +43,7 @@ static int F(Filter *f)
#endif #endif
const unsigned size = f->buf_len; const unsigned size = f->buf_len;
unsigned ic, jc, kc; unsigned ic;
unsigned cto;
unsigned char cto8; unsigned char cto8;
unsigned calls = 0, noncalls = 0, noncalls2 = 0; unsigned calls = 0, noncalls = 0, noncalls2 = 0;
unsigned lastnoncall = size, lastcall = 0; unsigned lastnoncall = size, lastcall = 0;
@@ -59,7 +58,7 @@ static int F(Filter *f)
#if 1 #if 1
for (ic = 0; ic < size - 5; ic++) for (ic = 0; ic < size - 5; ic++)
if (COND(b,ic) && get_le32(b+ic+1)+ic+1 >= size) if (COND(b,ic,lastcall) && get_le32(b+ic+1)+ic+1 >= size)
{ {
buf[b[ic+1]] |= 1; buf[b[ic+1]] |= 1;
} }
@@ -67,7 +66,7 @@ static int F(Filter *f)
{ {
int i = size - 6; int i = size - 6;
do { do {
if (COND(b,i) && get_le32(b+i+1)+i+1 >= size) if (COND(b,i,lastcall) && get_le32(b+i+1)+i+1 >= size)
buf[b[i+1]] |= 1; buf[b[i+1]] |= 1;
} while (--i >= 0); } while (--i >= 0);
} }
@@ -101,13 +100,13 @@ static int F(Filter *f)
return -1; return -1;
cto8 = (unsigned char) ic; cto8 = (unsigned char) ic;
} }
cto = (unsigned)cto8 << 24; unsigned const cto = (unsigned)cto8 << 24;
for (ic = 0; ic < size - 5; ic++) for (ic = 0; ic < size - 5; ic++)
{ {
if (!COND(b,ic)) if (!COND(b,ic,lastcall))
continue; continue;
jc = get_le32(b+ic+1)+ic+1; unsigned const jc = get_le32(b+ic+1)+ic+1;
// try to detect 'real' calls only // try to detect 'real' calls only
if (jc < size) if (jc < size)
{ {
@@ -117,8 +116,9 @@ static int F(Filter *f)
if (ic - lastnoncall < 5) if (ic - lastnoncall < 5)
{ {
// check the last 4 bytes before this call // check the last 4 bytes before this call
unsigned kc;
for (kc = 4; kc; kc--) for (kc = 4; kc; kc--)
if (COND(b,ic-kc) && b[ic-kc+1] == cto8) if (COND(b,ic-kc,lastcall) && b[ic-kc+1] == cto8)
break; break;
if (kc) if (kc)
{ {
@@ -164,11 +164,12 @@ static int U(Filter *f)
const unsigned size5 = f->buf_len - 5; const unsigned size5 = f->buf_len - 5;
const unsigned addvalue = f->addvalue; const unsigned addvalue = f->addvalue;
const unsigned cto = f->cto << 24; const unsigned cto = f->cto << 24;
unsigned lastcall = 0;
unsigned ic, jc; unsigned ic, jc;
for (ic = 0; ic < size5; ic++) for (ic = 0; ic < size5; ic++)
if (COND(b,ic)) if (COND(b,ic,lastcall))
{ {
jc = get_be32(b+ic+1); jc = get_be32(b+ic+1);
if (b[ic+1] == f->cto) if (b[ic+1] == f->cto)
@@ -176,7 +177,7 @@ static int U(Filter *f)
set_le32(b+ic+1,jc-ic-1-addvalue-cto); set_le32(b+ic+1,jc-ic-1-addvalue-cto);
f->calls++; f->calls++;
ic += 4; ic += 4;
f->lastcall = ic+1; f->lastcall = lastcall = ic+1;
} }
else else
f->noncalls++; f->noncalls++;
+13 -5
View File
@@ -95,17 +95,25 @@ cjt16_L2:
;; ============= 32-BIT CALLTRICK & JUMPTRICK ;; ============= 32-BIT CALLTRICK & JUMPTRICK
;; ============= ;; =============
;; call & jump trick : 2 in 1 ;; call & jump & Jxx trick : 3 in 1
%macro cjt32 1 %macro cjt32 1
%ifdef __CALLTR00__ %ifdef __CALLTR00__
mov bh, 0x0f ; avoid displ and literal in same instr
mov ecx, 'TEXL' mov ecx, 'TEXL'
calltrickloop: calltrickloop:
mov al, [edi] mov al, [edi]
inc edi inc edi
sub al, 0xE8 sub al, 0x80 ; base of Jxx <d32>
cmp al, 0x8f - 0x80 ; span of Jxx <d32>
ja ct2 ; not Jxx <d32>
cmp byte [edi -2], bh ; prefix opcode of Jxx <d32>
je ct3
ct2:
sub al, 0xE8 - 0x80 ; base of JMP/CALL <d32>
ct1: ct1:
cmp al, 1 cmp al, 0xE9 - 0xE8 ; span of JMP/CALL <d32>
ja calltrickloop ja calltrickloop
ct3:
%ifdef __CTCLEVE1__ %ifdef __CTCLEVE1__
cmp byte [edi], '?' cmp byte [edi], '?'
jnz calltrickloop jnz calltrickloop
@@ -122,14 +130,14 @@ ct1:
xchg al, ah xchg al, ah
%endif; __CALLTR02__ %endif; __CALLTR02__
sub eax, edi sub eax, edi
sub bl, 0xE8 sub bl, 0xE8 ; base of JMP/CALL <d32>
%ifnidn %1,0 %ifnidn %1,0
add eax, %1 add eax, %1
%endif %endif
mov [edi], eax mov [edi], eax
add edi, byte 5 add edi, byte 5
mov al, bl mov al, bl
loop ct1 loop ct1 ; no Jxx <d32> next: needs 0x0f prefix first
%else; __CALLTR10__ %else; __CALLTR10__
;; 32-bit call XOR jump trick ;; 32-bit call XOR jump trick
mov ecx, 'TEXL' mov ecx, 'TEXL'