模糊测试 Arrow C++#

为了使对无效输入的处理更加健壮,我们在 Arrow C++ 功能集的几个部分启用了模糊测试,目前包括

  • IPC 流格式

  • IPC 文件格式

  • Parquet 文件格式

我们欢迎任何扩展模糊测试范围并涵盖摄取潜在无效或恶意数据的领域的贡献。

模糊测试目标和工具#

通过传递 -DARROW_FUZZING=ON CMake 选项(或等效地,使用 fuzzing 预设),您将构建与上述 Arrow 功能相对应的模糊测试目标,以及其他相关工具。

生成种子语料库#

模糊测试本质上是通过随机变异先前测试的输入来探索域空间,而没有对被模糊测试的区域有任何高级理解。但是,域空间非常大,因此仅靠这种策略可能无法真正产生任何“有趣”的输入。

因此,为了指导这个过程,提供一个种子语料库非常重要,该语料库包含有效的(或无效但非凡的)输入,模糊测试基础设施可以从中派生新的输入以进行测试。提供了一个脚本来自动执行此任务。假设模糊测试可执行文件可以在 build/debug 中找到,则可以按以下方式生成种子语料库

$ ./build-support/fuzzing/generate_corpuses.sh build/debug

持续模糊测试基础设施#

模糊测试过程在计算上很密集,因此受益于专用计算设施。Arrow C++ 由 Google 运营的 OSS-Fuzz 持续模糊测试基础设施进行测试。

由 OSS-Fuzz 发现的问题会被通知并提供给 核心开发者 的有限集合。如果您是 Arrow 核心开发者,并希望被添加到该列表中,您可以在 邮件列表 上询问。

在本地复制#

当模糊测试发现崩溃时,通常很有用的是下载用于产生崩溃的数据,并使用它来重现崩溃,以便调试和调查。

假设您位于 cpp 内的子目录中,以下命令将允许您构建具有调试信息和启用各种消毒剂检查的模糊测试目标。

$ cmake .. --preset=fuzzing

然后,假设您已下载崩溃数据文件(我们称之为 testcase-arrow-ipc-file-fuzz-123465),您可以通过在该文件上运行受影响的模糊测试目标来重现崩溃

$ build/debug/arrow-ipc-file-fuzz testcase-arrow-ipc-file-fuzz-123465

(您可能希望在调试器下运行该命令,以便更仔细地检查程序状态)

使用 conda#

模糊测试可执行文件必须使用 clang 编译并链接到提供模糊测试运行时的库。如果您使用 conda 来提供您的依赖项,您可能需要在构建模糊测试目标之前安装它们

$ conda install clang clangxx compiler-rt
$ cmake .. --preset=fuzzing