gpt4 book ai didi

c++ - LLVM IR : Identifying Variables with Metadata Nodes

转载 作者:塔克拉玛干 更新时间:2023-11-02 23:37:09 29 4
gpt4 key购买 nike

目前我正在开发一种工具,该工具可以识别对任意程序的全局变量和字段变量的加载和存储访问。此外,访问的变量应该由它们的源级别名称/标识符来标识。为了完成这个,我将被诊断程序的源代码编译成带有调试信息的 LLVM IR。到目前为止一切顺利,生成的元数据节点包含所需的源级别标识符。但是,我无法将某些 LLVM IR 标识符和元数据中的信息联系起来。

例如,考虑一个类的静态成员:

 class TestClass {
public:
static int Number;
};

相应的 LLVM IR 如下所示:

@_ZN12TestClass6NumberE = external global i32, align 4

...
!15 = !DIDerivedType(tag: DW_TAG_member, name: "Number", scope: !"_ZTS12TestClass", file: !12, line: 5, baseType: !16, flags: DIFlagPublic | DIFlagStaticMember)

在这个受控示例中,我知道“@_ZN12TestClass6NumberE”是“Number”的标识符。但是,总的来说,我看不出如何找出哪些 IR 标识符对应于哪些元数据。

有人可以帮帮我吗?

最佳答案

由于似乎没有人能很好地解决我的问题,所以我将讲述我自己处理这个问题的不方便方法。 LLVM 生成的元数据节点包含有关代码的已定义类型和变量的信息。但是,没有关于哪些生成的 IR 变量对应于哪些源代码变量的信息。 LLVM 仅将 IR 指令的元数据信息与相应的源位置(行和列)链接起来。这是有道理的,因为 LLVM 元数据的主要任务不是分析而是调试。

不过,其中包含的信息并非毫无用处。我对这个问题的解决方案是使用 clang AST 来分析源代码。在这里,我们获得有关在哪个源位置访问哪个变量的信息。因此,为了在 LLVM IR 检测期间获取有关源变量身份的信息,我们只需要在 clang AST 分析期间将源位置映射到源变量身份。作为第二步,我们使用之前收集的信息执行 IR 检测。当我们在 IR 中遇到存储或加载指令时,我们会在该指令的元数据节点中搜索其对应的源位置。由于我们已将源位置映射到源变量标识,我们现在可以轻松访问 IR 指令的源变量标识。

那么,为什么我不直接使用 clang AST 来识别变量的存储和加载?因为在 AST 中区分读取和写入并不是一件简单的工作。 AST 可以很容易地告诉您访问了一个变量,但这取决于访问的变量是读取还是写入的操作。因此,我将不得不考虑每一个操作/运算符来确定变量是被写入/读取还是两者兼而有之。在这方面,LLVM 更简单、更底层,因此更不容易出错。此外,与 LLVM 相比,AST 中的实际检测(说出代码插入)要困难得多。由于这两个原因,我相信结合使用 clang AST 和 LLVM IR 检测是解决我的问题的最佳方案。

关于c++ - LLVM IR : Identifying Variables with Metadata Nodes,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34578398/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com