Skip to content

公式化Go逆向之指纹提取

Published: at 02:54 PM

本文中涉及到的项目:github.com/kN6jq/fingerScan

Table of Contents

Open Table of Contents

Hex view 提取

ImHex打开,搜索字符串,浏览了,发现存在类似指纹字符串,如下图所示:

image-20241218105726236

这种指纹提取比较简单,根据指纹内容的格式,找到规则开始的部分,写脚本提取就好了:

image-20241218105950874

如果读者对提取感兴趣,还可以尝试提取下这个指纹识别工具 P1finger中的指纹,相对于本文的案例fingerScan而言,P1finger的仓库中默认不存在指纹列表,这会使得你更享受提取成功所带来的成就感。

Runtime 提取

如果拿到的Go二进制程序存在符号表,可以在关键函数处打断点,通过动态调试的方式拿到相关数据数据。

GDB 调试

fingerScan 为例,先定位到json.Unmarshal符号表的地址,为0x51e520,如下所示:

go tool nm finger_scan_64 |grep unmarsha -i|grep json

image-20241218112254225

接着使用GDB 进行调试, 并在符号地址处打个断点:

gdb fringer_scan_64

(gdb) b *0x51e520

image-20241218112439903

打完断点后, 运行程序,当执行到断点处,使用命令

(gdb) display data

打印出json.Unmarshal()的第一个参数的值,结果如下图所示:

image-20241218112623067

实际上json.Unmarshal()的第一个参数的值的地址存在rax 寄存器中:

image-20241218112722142

通过display 命令可以看到 data 相关的信息,其中包括长度以及内存的起始地址,接下来我们直接将内存中data的值给dump出来:

dump memory fingerprint.out $rax $rax+6057050

image-20241218113216224

image-20241218113154160

IDA调试

ida同理,先找到json.Unmarshal的位置,在关键信息处打个断点:

image-20241218141246339

接着使用Wingdb 进行调试,当运行到断点处,去查看rax寄存器指向的地址,发现就存储着指纹信息:

image-20241218141339409

image-20241218141434617

image-20241218141643672

由于不知道偏移是多少rax + ?, 所以需要去写脚本去遍历才能把内存给dump下来。

但是不会。。。。。

总结

如果拿到的Go可执行文件存在符号表的话,可以试着用这种方法来提取一下,简单又有趣。

当然,如果使用了 ldflags='-s -w' 就没办法使用这种方式了。比如P1finger.

另外

波特师傅提到了几个常见调试的函数,如下:

regexp.MustCompile
os.Open
base64.StdEncoding.DecodeString
hex.DecodeString
aes.NewCipher

听说能抓到xray 中的一些正则,不过还没去实验。。。