参考:https://eternalsakura13.com/2020/08/23/afl/#more
接下来开始LLVM部分,第一次接触LLVM,这一篇就分析了afl-clang-fast.c,先这些吧,后面的pass部分还得慢慢分析。
afl-clang-fast.c
1.main 函数
-
打印信息
-
调用
find_obj
查找运行时库 -
调用
edit_params
设置参数,打印出来看一下
-
执行命令
2.find_obj 查找运行时库
- 获取环境变量 AFL_PATH 赋值给
afl_path
- 如果环境变量存在
tmp
赋值为 afl_path/afl-llvm-rt.o- 如果文件可读
obj_path
=afl_path
- 释放 并 return
- 不可读则直接释放
slash
指向第一个参数的之后一个 ‘/’ 的位置- 如果
slash
不为null- 取 ‘/’ 之前的字符串为
dir
slash
= ‘/’tmp
为 dir/afl-llvm-rt.o- 如果文件可读
obj_path
=dir
- 释放 并 return
- 不可读则直接释放
- 取 ‘/’ 之前的字符串为
- 最后如果上面两种都找不到,因为默认的AFL的MakeFile在编译的时候,会定义一个名为
AFL_PATH
的宏,其指向/usr/local/lib/afl
,会到这里找是否存在afl-llvm-rt.o
,如果存在设置obj_path
并直接返回 - 三种方式都找不到,则抛出异常
3.edit_params 设置参数
- 为
cc_params
分配大小为 (argc + 128) * 8 的空间 - 检查 argv[0] 中是否存在 ‘/’
- 如果不存在则
name
= argv[0] - 如果存在则一直找到最后一个/,并将其后面的字符串赋值给
name
- 如果不存在则
- 如果
name
为 ”afl-clang-fast++“- 获取环境变量 AFL_CXX 赋值给
alt_cxx
- 如果
alt_cxx
不为null,则第一个参数为alt_cxx
,否则,为"clang++"
- 获取环境变量 AFL_CXX 赋值给
- 如果
name
不为 ”afl-clang-fast++“- 获取环境变量 AFL_CC 赋值给
alt_cc
- 如果
alt_cc
不为null,则第一个参数为alt_cc
,否则,为"clang"
- 获取环境变量 AFL_CC 赋值给
- 依次设置"-Xclang"、“-load”、“Xclang”、“obj_path/afl-llvm-pass.o”、“-Qunused-arguments”
- 进入循环,一次读取传入的参数至
cc_params
中- 如果参数中有 “-m32”,置
bit_mode
= 32 - 如果参数中有 “armv7a-linux-androideabi”,置
bit_mode
= 32 - 如果参数中有 “-m64”,置
bit_mode
= 64 - 如果参数中有 “-x”,置
x_set
= 1 - 如果参数中有 “-fsanitize=address"或”-fsanitize=memory",置
asan_set
= 1 - 如果某个参数包含"FORTIFY_SOURCE",置
fortify_set
= 1 - 如果参数中有 “-Wl,-z,defs"或”-Wl,–no-undefined",则丢弃
- 保存参数
- 如果参数中有 “-m32”,置
- 如果有环境变量"AFL_HARDEN"
- 添加参数"-fstack-protector-all"
- 如果
fortify_set
= 0,添加参数"-D_FORTIFY_SOURCE=2"
- 如果
asan_set
= 0- 如果有环境变量"AFL_USE_ASAN"
- 如果有环境变量"AFL_USE_MSAN",则抛出异常
- 如果有环境变量"AFL_HARDEN",则抛出异常
- 添加参数"-U_FORTIFY_SOURCE"和"-fsanitize=address"
- 如果有环境变量"AFL_USE_MSAN"
- 如果有环境变量"AFL_USE_ASAN",则抛出异常
- 如果有环境变量"AFL_HARDEN",则抛出异常
- 添加参数"-U_FORTIFY_SOURCE"和"-fsanitize=memory"
- 如果有环境变量"AFL_USE_ASAN"
- 如果没有环境变量"AFL_DONT_OPTIMIZE"
- 添加参数"-g"、“-03”、“-funroll-loops”
- 如果有环境变量"AFL_NO_BUILTIN"
- 添加参数"-fno-builtin-strcmp"、 “-fno-builtin-strncmp” 、“-fno-builtin-strcasecmp”、 “-fno-builtin-strncasecmp”、 “-fno-builtin-memcmp”
- 添加参数 “-D__AFL_HAVE_MANUAL_CONTROL=1”、 “-D__AFL_COMPILER=1”、“-DFUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION=1”
- 添加两个宏
- 如果
x_set
不为0,添加参数"-x"、“none” - 进入switch
- 如果
bit_mode
=0,添加参数"obj_path/afl-llvm-rt.o" - 如果
bit_mode
=32,添加参数"obj_path/afl-llvm-rt-32.o" - 如果
bit_mode
=64,添加参数"obj_path/afl-llvm-rt-64.o"
- 如果
- 最后添加结束标志