c++ - LLVM 用函数替换操作数

标签 c++ llvm llvm-clang llvm-ir

使用 LLVM pass,我希望遍历 if(a==b) 形式的所有条件分支,并将这些语句更改为 if(func(a)==func (b)) 从而用函数调用 func(a) 的结果替换原始操作数 ab >函数(b)。只要发现 if(a==b) 形式的 if 语句,就会出现这种情况。

这里的a是操作数。我可以在我的 LLVM 传递中访问这个操作数,但我不能将它更改为函数的结果。我应该使用什么方法来实现这一目标。

可以假设 ab 总是相同的类型并且 func 接受任何类型的参数并返回相同的参数的类型。为简单起见,还可以假设 ab 是整数,并且 func 也返回一个整数。

最佳答案

详细说明我的评论(尽管有些方面仍不清楚)

采用以下简化:

  • 我们正在对整数进行操作
  • 要调用的函数已经定义好

我们可以在 llvm::Function 传递中做这样的事情:

bool runOnFunction(llvm::Function &CurFunc) override {
    bool hasChanged = false;

    // the llvm::Function to be called could be specified here
    auto *toCallFunc = [...];

    for (auto &bb : CurFunc) {
      auto *ti = bb.getTerminator();
      auto *bri = llvm::dyn_cast<llvm::BranchInst>(ti);
      if (!bri)
        continue;
      if (!bri->isConditional())
        continue;

      auto *cond = bri->getCondition();

      // please note that this cast is for integer comparisons
      // adjust according to your needs
      auto cmpi = llvm::dyn_cast<llvm::ICmpInst>(cond);
      if (!cmpi)
        continue;

      auto *opA = cmpi->getOperand(0);
      auto *opB = cmpi->getOperand(1);

      auto argsA = llvm::ArrayRef<llvm::Value *>(&opA, 1);
      auto argsB = llvm::ArrayRef<llvm::Value *>(&opB, 1);

      // note the insertion before the comparison operation
      auto *ciA = llvm::CallInst(toCallFunc, argsA, "funcA", cmpi);
      auto *ciB = llvm::CallInst(toCallFunc, argsB, "funcB", cmpi);

      cmpi->setOperand(1, opA);
      cmpi->setOperand(1, opB);
      hasChanged |= true;
    }

    return hasChanged;
  }

从那时起,您可以扩展和处理其他参数类型,具体取决于所需的处理。

关于c++ - LLVM 用函数替换操作数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48068157/

相关文章:

c++ - 苹果 clang ;将 C++11 与 libstdc++ 结合使用

基于堆栈的机器的 LLVM 后端

llvm-clang - LLVM 使用进位和零标志

swift - 在同一项目中设置 Vapor 和 Clang

c++ - 加快 C++ 中 double 的比较

c++ - 忽略 C++ 中的字节顺序标记,从流中读取

c++ - 在 GCC 上与 "-ffast-math"的 quiet_NaN 的浮点比较总是产生 true(!)

c++ - 如何将字符串操作为小写并存储在同一个变量中

algorithm - 如何构建具有无限循环的函数的后支配树?

Clang - 如何将 "Expr"作为字符串检索?