老文章档案 · 2003 年

用插件(plugin)的方式改变IDA Pro的边界线

天下资讯 · 破解文章 · 2003-06-09 · 作者:bpx 人气: · 出处:赢政天下收集整理)

用插件(plugin)的方式改变IDA Pro的边界线

(同时在看雪论坛(用bpx)http://www.chat001.com/forum/crackforum/index.html和说吧论坛(欧阳

锋)http://bbs.sayba.com/cgi-bin/forums.cgi?forum=49上发表。

在说吧论坛的附件中包含整个工程。如果没有ida pro sdk的朋友可将压缩包中的BorderPatch.plw复制到ida的plugin子目录就可以了。否则,将工程解压到sdk的plugin子目录。

IDA Pro,这个2001年世界最佳开发工具亚军(冠军是MS .net), 在功能上是一个近乎完美的工具。

4.50 加上了调试器,简直是如虎添翼。然而,对于使用中文Windows的用户,她却有一个小小的瑕疵

,那就是分界线显示为

"哪哪哪哪哪哪哪哪哪哪哪哪哪哪哪哪"

感觉不爽。以前想过改掉它,但没有成功。也不愿再多花更多时间。想等公司买了正版以后再说。后

来看雪论坛有高手贴出过修改idag.exe的方法。方法很不错。昨天看了IDA SDK, 发现有更好的办法

。那就是用插件。

修改idag.exe存在以下不足之处:

1. 每显示一行信息都要跳出去检查是不是边界线,对性能有一定影响。而插件只是在加载时patch边

界线生成的代码。对性能没有丝毫影响。

2. 版本更新后又要去修改,而用插件的方法理论上可以支持各种版本,且不用重编译。

3. 修改idag.exe不方便支持双字节边界线,用=====或------画面略显单调。而用插件用户可选择多

种边界线,如

0040113C ; ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

0040113D align 4

00401140

00401140 ; 〓〓〓〓〓〓〓〓 S U B R O U T I N E 〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓〓

00401140

00401140

00401140 CStatus::Free proc near ; CBoardDisplay::Free+8p

00401140 ; CHistory::Free+18p ...

00401140

00401140 arg_0= dword ptr 4

00401140

00401140 mov eax, [esp+arg_0]

00401144 push eax

00401145 call MemFree

0040114A add esp, 4

0040114D retn

0040114D CStatus::Free endp

0040114D

0040114D ; ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

0040113C ; ☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆

0040113D align 4

00401140

00401140 ; ★★★★★★★★ S U B R O U T I N E ★★★★★★★★★★★★★★★★★★★

00401140

00401140

00401140 CStatus::Free proc near ; CBoardDisplay::Free+8p

00401140 ; CHistory::Free+18p ...

00401140

00401140 arg_0= dword ptr 4

00401140

00401140 mov eax, [esp+arg_0]

00401144 push eax

00401145 call MemFree

0040114A add esp, 4

0040114D retn

0040114D CStatus::Free endp

0040114D

0040114D ; ☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆☆

以下是对这个插件的简单说明,详细内容请参阅源代码

ida边界生成函数分别为

bool MakeBorder();

bool MakeSolidBorder();

它们在ida.wll这个压缩动态连接库中。其中后者为函数的分界线。我们就patch这两个函数。

typedef bool (*BorderFunc)(void);

static bool PatchBorderFuncs(void)

{

BorderFunc func;

unsigned char* ptr, *ptr2;

int i, j;

// 获得要patch函数的地址

func = MakeBorder; // 这是thunk地址

ptr = (unsigned char*)**(BorderFunc**)((char*)func + 2); // 这才是函数在ida.wll

中的真实地址

...

}

如果仅仅想边界线显示为=========或-------------,那就太简单了,仅需将

push 0c4h 改成 push 2dh

push 0dbh 改成 push 3dh

如果想要显示双字节边界,除了patch以上二个函数外,还要修改sub_100732C4(),让它支持中文字

符边界,这样美观的多,你说呢?

用以上的方法虽解决了一个无关紧要问题,却让我们有了一个修改ida的一个方法! 以下是源代码:

/*

* This Border line patch

* By Xiao Han-Qing (bpx)

* April 5, 2003

*/

#include <ida.hpp>

#include <idp.hpp>

#include <bytes.hpp>

#include <loader.hpp>

#include <kernwin.hpp>

/*

MakeBorder()

{

10011E4C 55 push ebp

10011E4D 8B EC mov ebp,esp

10011E4F 83 C4 9C add esp,0FFFFFF9Ch

10011E52 F6 05 AE 85 0C 10 01 test byte ptr ds:[100C85AEh],1 ;如果这个值为1,就不

显示边界线

10011E59 74 43 je 10011E9E

10011E5B EB 14 jmp 10011E71

10011E5D 6A 00 push 0

10011E5F 68 C6 82 0A 10 push 100A82C6h

10011E64 E8 EF 07 00 00 call 10012658

10011E69 84 C0 test al,al

10011E6B 74 04 je 10011E71

10011E6D B0 01 mov al,1

10011E6F EB 2F jmp 10011EA0

10011E71 0F BE 15 F1 B4 0B 10 movsx edx,byte ptr ds:[100BB4F1h]

10011E78 4A dec edx

10011E79 74 E2 je 10011E5D

10011E7B 6A 4B push 4Bh ; 边界线的长度,需要patch成

4ch

10011E7D 68 C4 00 00 00 push 0C4h ; 就是这个丑陋字符,patch成

ThinBorder

10011E82 8D 4D 9C lea ecx,[ebp-64h]

10011E85 51 push ecx

10011E86 E8 39 14 06 00 call sub_100732C4 ; 这个函数里面要patch

10011E8B 83 C4 0C add esp,0Ch

10011E8E 8D 45 9C lea eax,[ebp-64h]

10011E91 C6 45 E7 00 mov byte ptr [ebp-19h],0 ; 因为将长度改成了4c, 故

patch成 mov byte ptr [ebp-18h], 0

10011E95 50 push eax

10011E96 E8 79 8C FF FF call 1000AB14

10011E9B 59 pop ecx

10011E9C EB 02 jmp 10011EA0

10011E9E 33 C0 xor eax,eax

10011EA0 8B E5 mov esp,ebp

10011EA2 5D pop ebp

10011EA3 C3 ret

}

*/

/*

MakeSolidBorder()

{

10011EA4 55 push ebp

10011EA5 8B EC mov ebp,esp

10011EA7 83 C4 9C add esp,0FFFFFF9Ch

10011EAA 56 push esi

10011EAB 57 push edi

10011EAC 6A 4B push 4Bh ; SolidBorder长度,patch 成

'push 4c'

10011EAE 68 DB 00 00 00 push 0DBh ; 丑陋的字符,patch成

SolidBorder

10011EB3 8D 45 9C lea eax,[ebp-64h]

10011EB6 50 push eax

10011EB7 E8 08 14 06 00 call sub_100732C4

10011EBC 8D 7D AB lea edi,[ebp-55h] ; 复制" S U B R O U T I N E "

的地址

10011EBF 83 C4 0C add esp,0Ch ; patch成lea edi, [ebp-54h],

落在偶地址

10011EC2 8B C7 mov eax,edi

10011EC4 BE C8 82 0A 10 mov esi,100A82C8h

10011EC9 B9 05 00 00 00 mov ecx,5

10011ECE 8D 55 9C lea edx,[ebp-64h]

10011ED1 F3 A5 rep movs dword ptr [edi],dword ptr [esi] ; 这段代码复制

" S U B R O U T I N E "

10011ED3 66 A5 movs word ptr [edi],word ptr [esi] ; patch成 movs

byte ptr[edi], byte ptr[esi]

10011ED5 C6 45 C0 DB mov byte ptr [ebp-40h],0DBh ; patch成4个

nop

10011ED9 C6 45 E7 00 mov byte ptr [ebp-19h],0 ; 改变了长度,

故patch成 mov byte ptr [ebp-18h], 0

10011EDD 52 push edx

10011EDE E8 31 8C FF FF call 1000AB14

10011EE3 59 pop ecx

10011EE4 5F pop edi

10011EE5 5E pop esi

10011EE6 8B E5 mov esp,ebp

10011EE8 5D pop ebp

10011EE9 C3 ret

}

*/

/*

sub_100732C4()

{

100732C4 55 push ebp

100732C5 8B EC mov ebp,esp

100732C7 57 push edi

100732C8 8A 45 0C mov al,byte ptr [ebp+0Ch] ; 我们要用双字节字符

作边界, 故

100732CB 8B 55 10 mov edx,dword ptr [ebp+10h] ; patch 成 mov eax,

dword ptr [ebp+0ch]

100732CE 8B 7D 08 mov edi,dword ptr [ebp+8]

100732D1 8A E0 mov ah,al ; patch 成 nop

100732D3 F7 C2 FC FF FF FF test edx,0FFFFFFFCh

100732D9 74 5D je 10073338

100732DB 66 89 07 mov word ptr [edi],ax

100732DE 8D 4C 17 FC lea ecx,[edi+edx-4]

100732E2 66 89 47 02 mov word ptr [edi+2],ax

100732E6 8B 07 mov eax,dword ptr [edi]

100732E8 C1 EA 03 shr edx,3

100732EB 74 43 je 10073330

100732ED 89 07 mov dword ptr [edi],eax

100732EF 89 47 04 mov dword ptr [edi+4],eax

100732F2 4A dec edx

100732F3 74 30 je 10073325

100732F5 89 47 08 mov dword ptr [edi+8],eax

100732F8 89 47 0C mov dword ptr [edi+0Ch],eax

100732FB 4A dec edx

100732FC 74 27 je 10073325

100732FE 89 47 10 mov dword ptr [edi+10h],eax

10073301 89 47 14 mov dword ptr [edi+14h],eax

10073304 4A dec edx

10073305 74 1E je 10073325

10073307 89 47 18 mov dword ptr [edi+18h],eax

1007330A 89 47 1C mov dword ptr [edi+1Ch],eax

1007330D 4A dec edx

1007330E 74 15 je 10073325

10073310 89 47 20 mov dword ptr [edi+20h],eax

10073313 89 47 24 mov dword ptr [edi+24h],eax

10073316 4A dec edx

10073317 74 0C je 10073325

10073319 89 47 28 mov dword ptr [edi+28h],eax

1007331C 89 47 2C mov dword ptr [edi+2Ch],eax

1007331F 8D 7F 30 lea edi,[edi+30h]

10073322 4A dec edx

10073323 75 C8 jne 100732ED

10073325 89 01 mov dword ptr [ecx],eax

10073327 89 41 FC mov dword ptr [ecx-4],eax

1007332A 8B 45 08 mov eax,dword ptr [ebp+8]

1007332D 5F pop edi

1007332E 5D pop ebp

1007332F C3 ret

}

*/

//--------------------------------------------------------------------------

//

// Initialize.

//

// IDA will call this function only once.

// If this function returns PLGUIN_SKIP, IDA will never load it again.

// If this function returns PLUGIN_OK, IDA will unload the plugin but

// remember that the plugin agreed to work with the database.

// The plugin will be loaded again if the user invokes it by

// pressing the hotkey or selecting it from the menu.

// After the second load the plugin will stay on memory.

// If this function returns PLUGIN_KEEP, IDA will keep the plugin

// in the memory. In this case the initialization function can hook

// into the processor module and user interface notification points.

// See the hook_to_notification_point() function.

//

//-----------------------

// Do our job here

//-----------------------

// length

#define Sig1 0x4b6a

#define ChgSig1 0x4c6a

// Ugly thin border

#define Sig2 0xc468

// call instruction byte

#define Call 0xe8

// Ugly solid border

#define Sig3 0xdb68

// 选择你喜欢的边界线,反注释

//-------------------------------------

//#define ThinBorder 0x2d2d968 // ==

//#define SolidBorder 0x3d3d68 // --

//-------------------------------------

// 以下适用于简体中文Windows!!!

//-------------------------------------

//#define ThinBorder 0xa5a968 //━

//#define SolidBorder 0xfea168 //〓

//------------------------------------

#define ThinBorder 0xeea168 //☆

#define SolidBorder 0xefa168 //★

//------------------------------------

//#define ThinBorder 0xaaa168 //—

//#define SolidBorder 0xf9a168 //※

//------------------------------------

// #define ThinBorder 0xf0a168 //○

// #define SolidBorder 0xf1a168 //●

//------------------------------------

// #define ThinBorder 0xf3a168 //◇

// #define SolidBorder 0xf4a168 //◆

//------------------------------------

// #define ThinBorder 0xf5a168 //□

// #define SolidBorder 0xf6a168 //■

//------------------------------------

// #define ThinBorder 0xf7a168 //△

// #define SolidBorder 0xf8a168 //▲

//------------------------------------

typedef bool (*BorderFunc)(void);

static bool PatchBorderFuncs(void)

{

BorderFunc func;

unsigned char* ptr, *ptr2;

int i, j;

// 获得要patch函数的thunk地址

func = MakeBorder;

// 这才是函数在ida.wll中的真实地址

ptr = (unsigned char*)**(BorderFunc**)((char*)func + 2);

// 最多搜索80个字符

for (i = 0; i < 80; i++) {

// 找到要patch的指令

// patch 'push 4bh'

if (*(unsigned short*)ptr == Sig1) { // search for 'push 0c4h'

*(unsigned short*)ptr = ChgSig1;

ptr += sizeof(short);

}

// patch 'push c4'

if (*(unsigned int*)ptr == Sig2) {

*(unsigned int*)ptr = ThinBorder; //

change to 'push 02dh

ptr += sizeof(int);

// 找到'call sub_100732C4'指令

for (ptr2 = ptr; *ptr2 != Call; ptr2++);

// 模拟'call'的过程跟踪到sub_100732C4地址

ptr2 += 5 + *(int*)(ptr2 + 1);

// 找到 mov al,byte ptr [ebp+0Ch]

for (j = 0; j < 30; j++) {

if ((*(unsigned int*)ptr2 & 0xffffff) == 0x0c458a) {

// patch成mov eax dword ptr [ebp+0ch]

*ptr2 = 0x8b;

ptr2 += 3;

}

// 找到mov ah, al

if (*(unsigned short*)ptr2 == 0xe08a) {

// patch 成nop

*(unsigned short*)ptr2 = 0x9090;

break;

}

ptr2++;

}

// patch mov byte ptr [ebp-19h],0 to mov byte ptr [ebp-18h],0

while (*(unsigned int*)ptr != 0xe745c6) ptr++;

*(unsigned int*)ptr = 0xe845c6;

break;

}

ptr++;

}

if (i == 80) return false;

func = MakeSolidBorder;

ptr = (unsigned char*)**(BorderFunc**)((char*)func + 2);

for (i = 0; i < 80; i++) {

// patch push 4b

if (*(unsigned short*)ptr == Sig1) { // search for 'push 0c4h'

*(unsigned short*)ptr = ChgSig1;

ptr += sizeof(short);

}

// patch push db

if (*(unsigned int*)ptr == Sig3) {

*(unsigned int*)ptr = SolidBorder; //

change to SolidBorder

ptr += sizeof(int);

}

if ((*(unsigned int*)ptr & 0xffffff) == 0xab7d8d) {

*(ptr+2) = 0xac;

ptr += 3;

}

if (*(unsigned int*)ptr == 0xdbc045c6) {

*(unsigned int*)ptr = 0x20c145c6;

ptr += sizeof(int);

// patch mov byte ptr [ebp-19h],0 to mov byte ptr [ebp-18h],0

while (*(unsigned int*)ptr != 0xe745c6) ptr++;

*(unsigned int*)ptr = 0xe845c6;

return true;

}

ptr++;

}

return false;

}

int init(void)

{

if (PatchBorderFuncs())

msg("Border line plugin loaded successfully!");

return PLUGIN_SKIP; // never load again

}

//--------------------------------------------------------------------------

//

// The plugin method

//

// This is the main function of plugin.

//

// It will be called when the user selects the plugin.

//

// arg - the input argument, it can be specified in

// plugins.cfg file. The default is zero.

//

//

void run(int arg)

{

}

//--------------------------------------------------------------------------

char comment[] = "Border line plugin";

char help[] = "Border line plugin for IDA Pro running under Simplified Chinese Windows";

//--------------------------------------------------------------------------

// This is the preferred name of the plugin module in the menu system

// The preferred name may be overriden in plugins.cfg file

char wanted_name[] = "Border line plugin";

char wanted_hotkey[] = "";

//--------------------------------------------------------------------------

//

// PLUGIN DESCRIPTION BLOCK

//

//--------------------------------------------------------------------------

extern "C" plugin_t PLUGIN = {

IDP_INTERFACE_VERSION,

0, // plugin flags

init, // initialize

NULL, //term, // terminate. this pointer may be NULL.

run, // invoke plugin

comment, // long comment about the plugin

// it could appear in the status line

// or as a hint

help, // multiline help about the plugin

注 意:

1. 不同版本的ida必须用其各自的sdk来编译这个plugin,否则ida不会加载其它版本sdk编译的plugin

2. 有些版本的ida(如ida4.30)其ida.wll必须用PeEditor将其代码段的特性改变为E000020,否则无法patch 其代码.

(出处:赢政天下收集整理)

相关资讯:

·彩虹狗破解工具的注册机

相关软件:

→ 特别推荐

→ 热点TOP10

我为人人《《==》》人人为我

关于我们 |

帮助(?)

| 广告服务 |

版权声明 |

商业合作 |

发展历程 |

加盟我们 |

联系我们

Copyright ? 1998-2003 winzheng.com

All Rights Reserved.

特别感谢 蓝芒科技 提供下载站及论坛服务器

2003-2004 年,宽带刚刚普及,下载站的文章区是许多人学电脑的第一课堂。
🕰 → 🤖 从那时到现在

当年一篇教程能让一台电脑焕然一新;今天的效率工具换成了 AI。 想知道当下最可靠的 AI 模型怎么选?看 赢政指数——我们用了 28 年的选软件严谨,现在用来评测大模型。

档案性质声明:本页为赢政天下(1998-2011)老文章的历史档案复原, 内容反映当年发表时的原貌——包括当年的技术表述、软件版本与观点,部分方法在今天已不适用或不合规,仅作互联网历史记录与研究用途, 不提供任何形式的下载。原始数据经由公共网络存档(Internet Archive)复原。发现问题请联系我们
← 返回老文章档案 · 软件史档案馆 · 赢政天下站史