From f275b12837ef4e506f07e56495b456d63a820ead Mon Sep 17 00:00:00 2001 From: John Reiser Date: Sun, 17 Dec 2000 18:33:42 +0000 Subject: [PATCH] call+jmp trick filter: add Jxx with 32-bit displacement src/fcto_ml.ch src/fcto_ml2.ch src/stub/macros.ash committer: jreiser 977078022 +0000 --- src/fcto_ml.ch | 8 +++++--- src/fcto_ml2.ch | 21 +++++++++++---------- src/stub/macros.ash | 18 +++++++++++++----- 3 files changed, 29 insertions(+), 18 deletions(-) diff --git a/src/fcto_ml.ch b/src/fcto_ml.ch index 1bdc9638..ebea56de 100644 --- a/src/fcto_ml.ch +++ b/src/fcto_ml.ch @@ -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 U u_cto32_e8_bswap_le #include "fcto_ml2.ch" @@ -77,7 +77,7 @@ #undef F #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 U u_cto32_e9_bswap_le #include "fcto_ml2.ch" @@ -88,7 +88,9 @@ #undef F #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 U u_cto32_e8e9_bswap_le #include "fcto_ml2.ch" diff --git a/src/fcto_ml2.ch b/src/fcto_ml2.ch index 3ce36488..e8b6e2fa 100644 --- a/src/fcto_ml2.ch +++ b/src/fcto_ml2.ch @@ -43,8 +43,7 @@ static int F(Filter *f) #endif const unsigned size = f->buf_len; - unsigned ic, jc, kc; - unsigned cto; + unsigned ic; unsigned char cto8; unsigned calls = 0, noncalls = 0, noncalls2 = 0; unsigned lastnoncall = size, lastcall = 0; @@ -59,7 +58,7 @@ static int F(Filter *f) #if 1 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; } @@ -67,7 +66,7 @@ static int F(Filter *f) { int i = size - 6; 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; } while (--i >= 0); } @@ -101,13 +100,13 @@ static int F(Filter *f) return -1; cto8 = (unsigned char) ic; } - cto = (unsigned)cto8 << 24; + unsigned const cto = (unsigned)cto8 << 24; for (ic = 0; ic < size - 5; ic++) { - if (!COND(b,ic)) + if (!COND(b,ic,lastcall)) 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 if (jc < size) { @@ -117,8 +116,9 @@ static int F(Filter *f) if (ic - lastnoncall < 5) { // check the last 4 bytes before this call + unsigned 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; if (kc) { @@ -164,11 +164,12 @@ static int U(Filter *f) const unsigned size5 = f->buf_len - 5; const unsigned addvalue = f->addvalue; const unsigned cto = f->cto << 24; + unsigned lastcall = 0; unsigned ic, jc; for (ic = 0; ic < size5; ic++) - if (COND(b,ic)) + if (COND(b,ic,lastcall)) { jc = get_be32(b+ic+1); 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); f->calls++; ic += 4; - f->lastcall = ic+1; + f->lastcall = lastcall = ic+1; } else f->noncalls++; diff --git a/src/stub/macros.ash b/src/stub/macros.ash index d8d7f408..c3a5091e 100644 --- a/src/stub/macros.ash +++ b/src/stub/macros.ash @@ -95,17 +95,25 @@ cjt16_L2: ;; ============= 32-BIT CALLTRICK & JUMPTRICK ;; ============= -;; call & jump trick : 2 in 1 +;; call & jump & Jxx trick : 3 in 1 %macro cjt32 1 %ifdef __CALLTR00__ + mov bh, 0x0f ; avoid displ and literal in same instr mov ecx, 'TEXL' calltrickloop: mov al, [edi] inc edi - sub al, 0xE8 + sub al, 0x80 ; base of Jxx + cmp al, 0x8f - 0x80 ; span of Jxx + ja ct2 ; not Jxx + cmp byte [edi -2], bh ; prefix opcode of Jxx + je ct3 +ct2: + sub al, 0xE8 - 0x80 ; base of JMP/CALL ct1: - cmp al, 1 + cmp al, 0xE9 - 0xE8 ; span of JMP/CALL ja calltrickloop +ct3: %ifdef __CTCLEVE1__ cmp byte [edi], '?' jnz calltrickloop @@ -122,14 +130,14 @@ ct1: xchg al, ah %endif; __CALLTR02__ sub eax, edi - sub bl, 0xE8 + sub bl, 0xE8 ; base of JMP/CALL %ifnidn %1,0 add eax, %1 %endif mov [edi], eax add edi, byte 5 mov al, bl - loop ct1 + loop ct1 ; no Jxx next: needs 0x0f prefix first %else; __CALLTR10__ ;; 32-bit call XOR jump trick mov ecx, 'TEXL'