这是如何使用 klee 符号执行测试有状态 API 吗?

Is this how to test a stateful API with klee symbolic execution?

我目前正在测试一些关于如何测试和模糊 C API 的方法。在此过程中,我发现 KLEE 以符号方式运行代码,这意味着它试图覆盖所有依赖于某些符号输入的分支并检查各种错误。我设法让它工作,现在我想问我的方法是否好,或者它是否有一些主要的缺点或问题。

假设我们有以下简单但有问题的 API:

#include <assert.h>

static int g_state;

void setState(int state) {
    g_state = state;
}

void run(void) {
    if (g_state == 123) {
        assert(0);
    }
}

如果状态设置为 123,然后调用 run(),则放置的断言失败。

为此,我用 KLEE 编写了以下符号测试:

#include "klee/klee.h"
#include "buggy_api.h"

int main(void) {
    for (int i = 0; i < 2; ++i) { // sequentially call 2 APIs
        int f_select = klee_choose(2); // what API to call
        if (f_select == 0) {
            int state = 0;
            klee_make_symbolic(&state, sizeof(state), "state");
            setState(state);
        } else if (f_select == 1) {
            run();
        }
    }
    return 0;
}

当 运行 KLEE 时,触发断言所需的调用序列几乎立即被发现。然后我尝试用其他一些函数扩展 API 并将断言隐藏在状态组合后面。 KLEE 再次发现了被植入的错误,但自然需要更长的时间。

这就是我如何有效地使用 KLEE 检查 API 的方法吗?或者是否有关于更好方法的文档?

为了使用 KLEE 测试 API,您确实需要编写一个调用它的驱动程序。你的效果很好,但我不确定你为什么要使用 for 循环?这个较小的例子应该有效:

#include "klee/klee.h"
#include "buggy_api.h"

int main(void) {
    int state;
    klee_make_symbolic(&state, sizeof(state), "state");
    setState(state);
    run();
    return 0;
}