Ghidra练手爆破Sublime Text 3.2 最新版本
本帖最后由 javacafe 于 2019-3-14 21:59 编辑今天刷网看到 Sublime Text 3.2 新版本发出, 突然想起前几天美国安全部发布的逆向工具Ghidra,还没怎么试用,所以就想既然闲着没事何不用
练练手,想到此,说干就干。
注:Ghidra 要求使用JDK 11
1.运行Ghidra,创建一个工程文件,然后File --> Import File 导入要逆向的文件,也就是sublime_text.exe,导入时会提示导入选择项,基本不用管直接导入。
2.然后当前工程页面直接点击导入的sublime_text.exe文件,或是选中sublime_text.exe按右键选择“Open With” 中的Code Browser打开也可。
3.等Ghidra分析完成,然后选择Windows菜单中的 Defined String 查看所有字符串,在字符串窗口下方的Filter输入框中输入“license”,列出了所有
带license的字符串。在sublime中输入注册码不正确时的提示信息是“That license key doesn't appear to be valid. Please check that you。。。”,所以
选择这个字符串。
4.在中间的机器码窗口直接定位到了该字符串的代码位置,然后直接点击其右上角的XREF地址。
在转到引用地址的代码后发现还是引用,继续点XREF,然后看到像是正常逻辑的代码。
然后点菜单工具栏的"Cf"样子的按纽或是按Ctrl+E,显示伪代码窗口
5. 简单查看伪代码
/* WARNING: Could not reconcile some variable overlaps */
void UndefinedFunction_1400911a8(longlong lParm1)
{
longlong lVar1;
longlong lVar2;
char cVar3;
int iVar4;
HANDLE hObject;
undefined8 ****ppppuVar5;
undefined8 ****ppppuVar6;
undefined auStack224 ;
int iStack192;
undefined8 ***pppuStack184;
undefined auStack176 ;
undefined auStack160 ;
undefined uStack144;
undefined auStack128 ;
undefined8 ****appppuStack112 ;
longlong lStack96;
ulonglong uStack88;
int iStack76;
undefined8 uStack72;
uStack72 = 0xfffffffffffffffe;
lVar1 = *(longlong *)(lParm1 + 8);
FUN_14035762e(*(undefined8 *)(*(longlong *)(*(longlong *)(lVar1 + 0x260) + 0x130) + 0x6f8),
&pppuStack184);
FUN_14030c5ca(appppuStack112,&pppuStack184);
FUN_14001f19e(&pppuStack184);
pppuStack184 = (undefined **)(((ulonglong)pppuStack184 >> 0x10 & 0xffff) << 0x10);
auStack160 = pslldq(ZEXT816(0xf),8);
auStack176 = 0;
uStack144 = 0;
auStack128 = auStack160;
FUN_14008f1a6(*(undefined8 *)(lVar1 + 0x250),&pppuStack184);
FUN_14008ee90(&pppuStack184);
if (lStack96 == 0) {
FUN_14008ef8d(&pppuStack184);
ppppuVar6 = &pppuStack184;
if (0xf < auStack160._0_8_) {
ppppuVar6 = (undefined8 ****)pppuStack184;
}
FUN_1400eb512(ppppuVar6);
FUN_140005858(&pppuStack184);
}
else {
lVar2 = *(longlong *)(lVar1 + 0x250);
iVar4 = FUN_14008f5cc(appppuStack112,lVar2 + 8,lVar2 + 4,&iStack76,lVar2 + 1);
lVar2 = *(longlong *)(lVar1 + 0x250);
*(bool *)lVar2 = iVar4 == 1;
if (iVar4 == 1) {
FUN_140005f36(lVar2 + 0x28,appppuStack112);
FUN_140006ab8(auStack224,appppuStack112);
auStack128 = (undefined)0x0 << 0x40;
iStack192 = iStack76;
pppuStack184 = &PTR_LAB_140563708;
FUN_14000ffca(auStack176,auStack224);
auStack128 = CONCAT88(auStack128._8_8_,&pppuStack184);
FUN_140005858(auStack224);
FUN_140189b75(&pppuStack184,120000);
FUN_140009c86(&pppuStack184);
FUN_14008eebe(appppuStack112);
FUN_14008ef8d(&pppuStack184);
ppppuVar6 = appppuStack112;
if (0xf < uStack88) {
ppppuVar6 = appppuStack112;
}
ppppuVar5 = &pppuStack184;
if (0xf < auStack160._0_8_) {
ppppuVar5 = (undefined8 ****)pppuStack184;
}
cVar3 = FUN_1400eb174(ppppuVar5,ppppuVar6,lStack96,1);
FUN_140005858(&pppuStack184);
if (cVar3 == 0) {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca7e8 - DAT_1407530a0,0);
}
hObject = (HANDLE)FUN_1400f5754(&LAB_14008f1df,(longlong)iStack76);
CloseHandle(hObject);
if (*(char *)(*(longlong *)(lVar1 + 0x250) + 1) == 0) {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca8cc - DAT_1407530a0,0);
//"Thanks for purchasing!"
}
else {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca892 - DAT_1407530a0,0);
// Hello! Thanks for trying out Sublime Text 3!\n\nSublime Text 3 is a paidupgrade from Sublime Text 2, and your license key is for Sublime Text2.\n\nWould you like to upgrade your license now?
} }
else {
if (iVar4 == 4) {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca8f6 - DAT_1407530a0,0);
//That license key has been invalidated, due to being shared.\n\nPlease emailsales@sublimetext.com to get your license key reissued.
}
else {
if (iVar4 == 3) {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca8e8 - DAT_1407530a0,0);
// That license key is no longer valid.
}
else {
if (iVar4 == 2) {
FUN_1400f7e6e(&DAT_140787ba0,0x166dca8da - DAT_1407530a0,0);
//That license key doesn't appear to be valid. Please check that you have entered all lines from the license key, including the BEGIN LICENSE and END LICENSE lines.
}
}
}
}
}
if (*(longlong *)(lVar1 + 0x2b0) != 0) {
FUN_140009cda(lVar1 + 0x278);
}
(**(code **)(**(longlong **)(lVar1 + 0x28) + 0x18))();
FUN_140005858(appppuStack112);
return;
}
6. 通过上面的代码分析,基本上认为 FUN_14008f5cc 是个关键方法,该方法值返回“1”代表注册成功。
iVar4 = FUN_14008f5cc(appppuStack112,lVar2 + 8,lVar2 + 4,&iStack76,lVar2 + 1);
lVar2 = *(longlong *)(lVar1 + 0x250);
*(bool *)lVar2 = iVar4 == 1;
if (iVar4 == 1) {
。。。
7. 然后点击FUN_14008f5cc转到该方法的代码,看上去是一堆计算,看着头大。
所以决定直接在函数开始修改为返回eax=1,Ghidra可以直接在代码窗口进行Patch。在需要patch的指令位置,点右键选择Patch Instruction即可。
8. 用Hex工具修改sublime_text.exe,运行,测试注册,输入任意字符,提示成功。
使用感触:因为只是简单使用,最大的感触是Ghidra的分析功能还是挺强大的,XREF比较到位,从定位license串到找到具体的注册信息计算代码就点两下鼠标就到了。
小白的简单试手,高手轻拍。
[ 由于国内PackageControl.io被墙,所以大家可使用 https://github.com/HBLong/channel_v3_daily 这个镜像下载插件]
本帖最后由 javacafe 于 2019-3-15 01:05 编辑
memory947 发表于 2019-3-15 00:10
修改成这样就 ...
比如原代码为:
14008f5cc 55 PUSH RBP
14008f5cd 41 57 PUSH R15
14008f5cf 41 56 PUSH R14
14008f5d1 41 55 PUSH R13
14008f5d3 41 54 PUSH R12
14008f5d5 56 PUSH RSI
14008f5d6 57 PUSH RDI
14008f5d7 53 PUSH RBX
14008f5d8 48 81 ec SUB RSP,0x248
48 02 00 00
修改为这样的
14008f5cc b8 01 00 MOV EAX,0x1
00 00
14008f5d1 48 cb RET
14008f5d3 41 54 PUSH R12
14008f5d5 56 PUSH RSI
14008f5d6 57 PUSH RDI
14008f5d7 53 PUSH RBX
14008f5d8 48 81 ec SUB RSP,0x248
48 02 00 00
冥界3大法王 发表于 2022-2-24 11:26
@smile1110 这个比IDA强在啥地方?
感觉二进制忍者也就那个样,交叉引用比IDA更方便些。
@冥界3大法王 ghidra能分析绝大部分嵌入式和单片机的固件,甚至北约的军用设备,并且背后是nsa在维护 楼主补丁呢{:301_1004:} 感谢分享。。 memory947 发表于 2019-3-14 21:29
楼主补丁呢
好吧,度盘自己下吧, 链接: https://pan.baidu.com/s/1jmWjuuDqjDGfB1EXt30q7A 提取码: ryh9 复制这段内容后打开百度网盘手机App,操作更方便哦 感谢分享 感谢分享 javacafe 发表于 2019-3-14 21:47
好吧,度盘自己下吧, 链接: https://pan.baidu.com/s/1jmWjuuDqjDGfB1EXt30q7A 提取码: ryh9 复制这段内 ...
注册给*** 要如何修改,给个思路 小小白 看着挺复杂!支持发帖!! 后面几个步骤不够详细= =,模拟了下无从下手,修改数据那步 140091282 83 f8 01 CMP EAX,0x1
修改成这样就行??