使用SymCC执行符号:不解释,编译

2020-07-08 19:55:29

美国马萨诸塞州波士顿,第29届USENIX安全研讨会(USENIX Security 20)论文集实用符号执行的一个主要障碍是速度,特别是与模糊测试等接近本地速度的解决方案相比。我们提出了一种基于编译的符号执行方法,其性能比最先进的实现要好几个数量级。我们介绍了SymCC,这是一个基于LLVM的C和C++编译器,它将并发执行直接构建到二进制文件中。软件开发人员可以将其用作clang和clang++的临时替代,我们将展示如何轻松添加对其他语言的支持。与KLEE相比,SymCC的速度提高了3个数量级,平均提高了12倍。它的性能也比QSYM高出两个数量级,平均提高了10倍。QSYM是一个最近在其他实现上表现出很大改进的系统。在实际软件上使用它,我们发现我们的方法始终实现了更高的覆盖率,我们在经过严格测试的OpenJPEG项目中发现了两个漏洞,这两个漏洞已经得到项目维护人员的确认,并分配了CVE标识符。

SymCC是一个基于编译器的快速符号执行引擎。在这一页上,我们提供了SymCC的源代码,白皮书中描述的实验的原始结果,以及如何自己复制这些实验的说明。

在本文中,我们描述了两组实验:首先在CGC程序上对SymCC进行基准测试,然后在真实软件上运行它。本节介绍如何复制我们的实验,并提供指向我们结果的链接。

我们通过BITS的方式使用了CGC程序的Linux移植。构建SymCC时需要支持32位编译(请参阅docs/32-bit.txt;这不是Dockerfile的一部分,因为它将使容器的构建时间翻一番,同时只为少数用户提供价值)。然后,您可以简单地将cc=/path/导出到/symcc,cxx=/path/导出到/sym++和SYMCC_NO_SYMBOL_INPUT=1,并照常构建CGC程序(即通过调用它们的build.sh脚本)。

在SYMCC_NO_SYMBOL_INPUT=1的原始POV输入上运行程序以测量纯执行时间,并取消设置用于符号执行的环境变量。为了评估覆盖范围,我们在每个生成的输入上运行AFL-showmap和AFL仪表化的CGC计划,并累计每个计划的结果覆盖图,从而为每个CGC计划生成一组覆盖的图条目。然后,可以将这些集合的大小输入到论文中提出的评分公式中。

对于Klee和QSYM,我们使用了这里描述的设置,但是使用了由cb-multios构建的常规32位二进制文件。

真实软件的分析总是遵循相同的过程。假设您已经导出了CC=symcc,cxx=sym++和SYMCC_NO_SYMBOL_INPUT=1,首先下载代码,然后使用自己的构建系统构建它,最后取消设置SYMCC_NO_SYMBOL_INPUT并与AFL协同分析程序(这需要为AFL第二次构建,请参见docs/Fuzzing.txt)。我们使用AFL 2.56B并使用AFL_USE_ASAN=1构建目标。请注意,Fuzing辅助对象已经安装在Docker容器中。

OpenJPEG(我们的结果):我们使用修订版1f1e9682,使用CMake构建,如项目的INSTALL.md中所述(添加-DBUILD_Thirdparty=on以确保第三方库也使用SymCC编译),并分析bin/opj_despress-i@@-o/tmp/image.pgm;语料库由测试文件file1.jp2和file8.jp2组成。

libarchive(我们的结果):我们使用修订版9ebb2484,按照Poject';安装中的描述使用CMake构建(但添加了-DCMAKE_BUILD_TYPE=RELEASE),并分析了bin/bsdtar TF@@;语料库只由一个包含字符";A";的虚拟文件组成。

tcpdump(我们的结果):我们构建了tcpdump和libpcap;为了让前者找到后者,只需将源目录紧挨着放在同一文件夹中。我们使用libpcap的修订版d615abec和tcpdump的修订版d57927e1。我们首先使用./configure&;&;make构建libpcap,然后使用./configure&;&;make构建tcpdump,并分析tcpdump/tcpdump-e-r@@;语料库只由一个包含字符";A";的虚拟文件组成。

所有实验均使用一个AFL主进程、一个辅助AFL进程和一个SymCC进程。我们让它们运行24小时,并将每一个重复30次,以创建本文中的图形;AFL贴图密度是从二级AFL过程的lot_data文件中提取的,列map_size。

QSYM实验使用了类似的设置,根据QSYM作者的说明用QSYM替换SymCC,并用AFL运行它。

如果您有任何不清楚之处或需要更多信息,请随时与我们联系。