已经说了三种反汇编引擎了,再一起学习一种radare2,这个开源项目不仅仅时做反汇编,还有其他功能等着我们去发掘,当然可以根据自己的需求选择合适的反汇编引擎,因为之前的文章都是简单的把反汇编引擎简单跑起来,并没有去讲到所有的API的使用,有兴趣的同学可以深入研究一下,记得一起分享下鸭;

Radare2,拥有非常强大的功能,包括反汇编、调试、打补丁、虚拟化等等,而且可以运行在几乎所有的主流平台上(GNU/Linux、Windows、BSD、iOS、OSX……)

github:https://github.com/radareorg/radare2
官网:

0x01:官网有提供二进制文件的下载,不过作者还是建议在本地去编译;

//cd master --> cd sys --> ./install.sh
curits@curits-virtual-machine:~/Desktop/radare2-master/sys$ ./install.sh
LD libr_socket.so
make[1]: curl: Command not found
Makefile:266: recipe for target 'capstone-4.0.2.tar.gz' failed
make[1]: *** [capstone-4.0.2.tar.gz] Error 127
make[1]: *** Waiting for unfinished jobs....
ar: creating libr_winkd.a
Makefile:56: recipe for target 'all' failed
make: *** [all] Error 2
//报错了,没有curl那就安装
curits@curits-virtual-machine:~/Desktop/radare2-master/sys$ sudo apt-get install curl
//curl 安装成功之后
curits@curits-virtual-machine:~/Desktop/radare2-master/sys$ ./install.sh
...........................
mkdir -p "/usr/local/share/radare2/4.6.0-git/"
/bin/sh sys/ldconfig.sh
/bin/sh ./configure-plugins --rm-static //usr/local/lib/radare2/last/
configure-plugins: Loading ./plugins.cfg ..
Removed 0 shared plugins that are already static

0x02:命令行使用方法
Radare2 在命令行下有一些小工具可供使用:

radare2:十六进制编辑器和调试器的核心,通常通过它进入交互式界面;
rabin2:从可执行二进制文件中提取信息;
rasm2:汇编和反汇编;
rahash2:基于块的哈希工具;
radiff2:二进制文件或代码差异比对;
rafind2:查找字节模式;
ragg2:r_egg 的前端,将高级语言编写的简单程序编译成x86、x86-64和ARM的二进制文件;
rarun2:用于在不同环境中运行程序;
rax2:数据格式转换;

curits@curits-virtual-machine:~/Desktop/radare2-master$ ra
rabin2     radiff2    ragg2      ranlib     rasign2    rasttopnm  rawtopgm   rax2       
radare2    rafind2    rahash2    rarun2     rasm2      raw        rawtoppm

radare2

curits@curits-virtual-machine:~/Desktop/radare2-master$ radare2 -h
Usage: r2 [-ACdfLMnNqStuvwzX] [-P patch] [-p prj] [-a arch] [-b bits] [-i file]
          [-s addr] [-B baddr] [-m maddr] [-c cmd] [-e k=v] file|pid|-|--|=
 --           run radare2 without opening any file
 -            same as 'r2 malloc://512'
 =            read file from stdin (use -i and -c to run cmds)
 -=           perform !=! command to run all commands remotely
 -0           print \x00 after init and every command
 -2           close stderr file descriptor (silent warning messages)
 -a [arch]    set asm.arch
 -A           run 'aaa' command to analyze all referenced code
 -b [bits]    set asm.bits
 -B [baddr]   set base address for PIE binaries
 -c 'cmd..'   execute radare command
 -C           file is host:port (alias for -c+=http://%s/cmd/)
 -d           debug the executable 'file' or running process 'pid'
 -D [backend] enable debug mode (e cfg.debug=true)
 -e k=v       evaluate config var
 -f           block size = file size
 -F [binplug] force to use that rbin plugin
 -h, -hh      show help message, -hh for long
 -H ([var])   display variable
 -i [file]    run script file
 -I [file]    run script file before the file is opened
 -k [OS/kern] set asm.os (linux, macos, w32, netbsd, ...)
 -l [lib]     load plugin file
 -L           list supported IO plugins
 -m [addr]    map file at given address (loadaddr)
 -M           do not demangle symbol names
 -n, -nn      do not load RBin info (-nn only load bin structures)
 -N           do not load user settings and scripts
 -NN          do not load any script or plugin
 -q           quiet mode (no prompt) and quit after -i
 -qq          quit after running all -c and -i
 -Q           quiet mode (no prompt) and quit faster (quickLeak=true)
 -p [prj]     use project, list if no arg, load if no file
 -P [file]    apply rapatch file and quit
 -r [rarun2]  specify rarun2 profile to load (same as -e dbg.profile=X)
 -R [rr2rule] specify custom rarun2 directive
 -s [addr]    initial seek
 -S           start r2 in sandbox mode
 -T           do not compute file hashes
 -u           set bin.filter=false to get raw sym/sec/cls names
 -v, -V       show radare2 version (-V show lib versions)
 -w           open file in write mode
 -x           open without exec-flag (asm.emu will not work), See io.exec
 -X           same as -e bin.usextr=false (useful for dyldcache)
 -z, -zz      do not load strings or load them even in raw
//调试二进制文件或进程
curits@curits-virtual-machine:~/Desktop/radare2-master$ sudo radare2 -d "/home/curits/Desktop/a.out"
Process with PID 30648 started...
= attach 30648 30648
bin.baddr 0x560384b60000
Using 0x560384b60000
asm.bits 64
 -- Remember that word: C H A I R
[0x7fe205753090]> 
[0x7fe205753090]> 

rabin2

curits@curits-virtual-machine:~/Desktop/radare2-master$ rabin2 -h
Usage: rabin2 [-AcdeEghHiIjlLMqrRsSUvVxzZ] [-@ at] [-a arch] [-b bits] [-B addr]
              [-C F:C:D] [-f str] [-m addr] [-n str] [-N m:M] [-P[-P] pdb]
              [-o str] [-O str] [-k query] [-D lang symname] file
 -@ [addr]       show section, symbol or import at addr
 -A              list sub-binaries and their arch-bits pairs
 -a [arch]       set arch (x86, arm, .. or <arch>_<bits>)
 -b [bits]       set bits (32, 64 ...)
 -B [addr]       override base address (pie bins)
 -c              list classes
 -cc             list classes in header format
 -C [fmt:C:D]    create [elf,mach0,pe] with Code and Data hexpairs (see -a)
 -d              show debug/dwarf information
 -D lang name    demangle symbol name (-D all for bin.demangle=true)
 -e              entrypoint
 -ee             constructor/destructor entrypoints
 -E              globally exportable symbols
 -f [str]        select sub-bin named str
 -F [binfmt]     force to use that bin plugin (ignore header check)
 -g              same as -SMZIHVResizcld -SS -SSS -ee (show all info)
 -G [addr]       load address . offset to header
 -h              this help message
 -H              header fields
 -i              imports (symbols imported from libraries)
 -I              binary info
 -j              output in json
 -k [sdb-query]  run sdb query. for example: '*'
 -K [algo]       calculate checksums (md5, sha1, ..)
 -l              linked libraries
 -L [plugin]     list supported bin plugins or plugin details
 -m [addr]       show source line at addr
 -M              main (show address of main symbol)
 -n [str]        show section, symbol or import named str
 -N [min:max]    force min:max number of chars per string (see -z and -zz)
 -o [str]        output file/folder for write operations (out by default)
 -O [str]        write/extract operations (-O help)
 -p              show physical addresses
 -P              show debug/pdb information
 -PP             download pdb file for binary
 -q              be quiet, just show fewer data
 -qq             show less info (no offset/size for -z for ex.)
 -Q              show load address used by dlopen (non-aslr libs)
 -r              radare output
 -R              relocations
 -s              symbols
 -S              sections
 -SS             segments
 -SSS            sections mapping to segments
 -t              display file hashes
 -T              display file signature
 -u              unfiltered (no rename duplicated symbols/sections)
 -U              resoUrces
 -v              display version and quit
 -V              Show binary version information
 -w              display try/catch blocks
 -x              extract bins contained in file
 -X [fmt] [f] .. package in fat or zip the given files and bins contained in file
 -z              strings (from data section)
 -zz             strings (from raw bins [e bin.rawstr=1])
 -zzz            dump raw strings to stdout (for huge files)
 -Z              guess size of binary program
Environment:
 RABIN2_LANG:      e bin.lang         # assume lang for demangling
 RABIN2_NOPLUGINS: # do not load shared plugins (speedup loading)
 RABIN2_DEMANGLE=0:e bin.demangle     # do not demangle symbols
 RABIN2_MAXSTRBUF: e bin.maxstrbuf    # specify maximum buffer size
 RABIN2_STRFILTER: e bin.str.filter   #  r2 -qc 'e bin.str.filter=??' -
 RABIN2_STRPURGE:  e bin.str.purge    # try to purge false positives
 RABIN2_DEBASE64:  e bin.debase64     # try to debase64 all strings
 RABIN2_DMNGLRCMD: e bin.demanglercmd # try to purge false positives
 RABIN2_PDBSERVER: e pdb.server       # use alternative PDB server
 RABIN2_SYMSTORE:  e pdb.symstore     # path to downstream symbol store
 RABIN2_PREFIX:    e bin.prefix       # prefix symbols/sections/relocs with a specific string
 R2_CONFIG:        # sdb config file

//得到二进制文件信息
curits@curits-virtual-machine:~/Desktop/radare2-master$ rabin2 -I /home/curits/Desktop/a.out 
arch     x86
baddr    0x0
binsz    6441
bintype  elf
bits     64
canary   false
class    ELF64
compiler GCC: (Ubuntu 7.5.0-3ubuntu1~18.04) 7.5.0
crypto   false
endian   little
havecode true
intrp    /lib64/ld-linux-x86-64.so.2
laddr    0x0
lang     c
linenum  true
lsyms    true
machine  AMD x86-64 architecture
maxopsz  16
minopsz  1
nx       true
os       linux
pcalign  0
pic      true
relocs   true
relro    full
rpath    NONE
sanitiz  false
static   false
stripped false
subsys   linux
va       true

当我们拿到一个二进制文件时,第一步就是获取关于它的基本信息,这时候就可以使用 rabin2。rabin2 可以获取包括 ELF、PE、Mach-O、Java CLASS 文件的区段、头信息、导入导出表、数据段字符串、入口点等信息,并且支持多种格式的输出。

下面介绍一些常见的用法:(我还会列出其他实现类似功能工具的用法,你可以对比一下它们的输出)

-I:最常用的参数,它可以打印出二进制文件信息,其中我们需要重点关注其使用的安全防护技术,如 canary、pic、nx 等。(file、chekcsec -f)
-e:得到二进制文件的入口点。(`readelf -h`)
-i:获得导入符号表,RLT中的偏移等。(readelf -r)
-E:获得全局导出符号表。
-s:获得符号表。(readelf -s)
-l:获得二进制文件使用到的动态链接库。(ldd)
-z:从 ELF 文件的 .rodare 段或 PE 文件的 .text 中获得字符串。(strings -d)
-S:获得完整的段信息。(readelf -S)
-c:列出所有类,在分析 Java 程序是很有用。

下面要讲到的就是本文的主题辣,反汇编引擎的使用;

0x03:具体的使用方法可以参照 https://book.rada.re/tools/rasm2/disassemble.html
使用rasm2进行反汇编:

curits@curits-virtual-machine:~/Desktop/radare2-master$ rasm2 -h
'Usage: rasm2 [-ACdDehLBvw] [-a arch] [-b bits] [-o addr] [-s syntax]
             [-f file] [-F fil:ter] [-i skip] [-l len] 'code'|hex|-
 -a [arch]    Set architecture to assemble/disassemble (see -L)
 -A           Show Analysis information from given hexpairs
 -b [bits]    Set cpu register size (8, 16, 32, 64) (RASM2_BITS)
 -B           Binary input/output (-l is mandatory for binary input)
 -c [cpu]     Select specific CPU (depends on arch)
 -C           Output in C format
 -d, -D       Disassemble from hexpair bytes (-D show hexpairs)
 -e           Use big endian instead of little endian
 -E           Display ESIL expression (same input as in -d)
 -f [file]    Read data from file
 -F [in:out]  Specify input and/or output filters (att2intel, x86.pseudo, ...)
 -h, -hh      Show this help, -hh for long
 -i [len]     ignore/skip N bytes of the input buffer
 -j           output in json format
 -k [kernel]  Select operating system (linux, windows, darwin, ..)
 -l [len]     Input/Output length
 -L           List Asm plugins: (a=asm, d=disasm, A=analyze, e=ESIL)
 -o,-@ [addr] Set start address for code (default 0)
 -O [file]    Output file name (rasm2 -Bf a.asm -O a)
 -p           Run SPP over input for assembly
 -q           quiet mode
 -r           output in radare commands
 -s [syntax]  Select syntax (intel, att)
 -v           Show version information
 -x           Use hex dwords instead of hex pairs when assembling.
 -w           What's this instruction for? describe opcode
 If '-l' value is greater than output length, output is padded with nops
 If the last argument is '-' reads from stdin
Environment:
 RASM2_NOPLUGINS  do not load shared plugins (speedup loading)
 RASM2_ARCH       same as rasm2 -a
 RASM2_BITS       same as rasm2 -b
 R_DEBUG          if defined, show error messages and crash signal

curits@curits-virtual-machine:~/Desktop$ sudo rasm2 -a x86 -b 64 -d "488d 2551 3f60 01e8 d400 0000"
lea rsp, [rip + 0x1603f51]
call 0xe0

curits@curits-virtual-machine:~/Desktop/radare2-master$ rasm2 -a x86 -b 64 'mov ebx,520'
bb08020000
curits@curits-virtual-machine:~/Desktop/radare2-master$ rasm2 -d bb08020000
mov ebx, 0x208
curits@curits-virtual-machine:~/Desktop/radare2-master$ rasm2 -D bb08020000
0x00000000   5               bb08020000  mov ebx, 0x208

Logo

更多推荐