Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to Insert a LLVM Instruction?

Tags:

c++

llvm

llvm-ir

I've been searching for hours and I can't find anything that could help me. I'm working on a project that involves a FunctionPass. I've implemented a runOnFunction(Function &f) method and that's working fine. Basically it needs to:

1) Detect a store instruction

2) Convert the memory address of the store instruction to an Integer

3) Alter the integer using a bitwise AND operation (0000FFFF)

4) Convert the integer back into the pointer

So far I've got the following:

 virtual bool runOnFunction(Function &F) {
  for (Function::iterator bb = F.begin(), bbe = F.end(); bb != bbe; ++bb) {
    BasicBlock& b = *bb;
    for (BasicBlock::iterator i = b.begin(), ie = b.end(); i != ie; ++i) {
      if(StoreInst *si = dyn_cast<StoreInst>(&*i)) {
        PtrToIntInst* ptrToInt = new PtrToIntInst(si->getPointerOperand(), IntegerType::get(si->getContext(), 32), "", si);
      }
    }
  }
  return true;
}

I can't for the life of me figure out how to actually insert the instruction, or even find a way to create an AND instruction. If anyone could point me in the right direction, that would be great.

Thanks in advance.

like image 899
KritSandvich Avatar asked Nov 13 '12 22:11

KritSandvich


3 Answers

I recommend taking a look at the Programmer's Manual - it has a pretty decent coverage of the basics.

In particular, there's a section about creating and inserting new instructions. The simplest way is just to provide an existing instruction as the last argument for the new instruction's constructor, which will then insert that instruction immediately before the existing one.

Alternatively, you can pass the enclosing basic block if you just want to add to its end (but remember you need to take care of the terminator!). Finally, you can just call getInstList() on the enclosing basic block, then insert or push_back to insert new instructions there.

As an aside, you don't have to iterate over all blocks and then over all instructions in each, you can just iterate over the instructions directly; see the section about the instruction iterator in the programmer's manual.

like image 140
Oak Avatar answered Oct 19 '22 19:10

Oak


 virtual bool runOnFunction(Function &F) {
  for (Function::iterator bb = F.begin(), bbe = F.end(); bb != bbe; ++bb) {
    BasicBlock &b = *bb;
    for (BasicBlock::iterator i = b.begin(), ie = b.end(); i != ie; ++i) {
      if (StoreInst *si = dyn_cast<StoreInst>(&*i)) {
        IRBuilder Builder(si);
        Value *StoreAddr = Builder.CreatePtrToInt(si->getPointerOperand(), Builder.getInt32Ty());
        Value *Masked = Builder.CreateAnd(StoreAddr, 0xffff);
        Value *AlignedAddr = Builder.CreateIntToPtr(Masked, si->getPointerOperand()->getType());
        // ...
      }
    }
  }
  return true;
}
like image 35
Nick Lewycky Avatar answered Oct 19 '22 17:10

Nick Lewycky


You can use an IRBuilder to easily insert new instructions before another instruction or at the end of a basic block.

Alternatively, if you need to insert an instruction after another one, you need to use the instruction list in the containing basic block:

BasicBlock *pb = ...; 
Instruction *pi = ...; 
Instruction *newInst = new Instruction(...); 

pb->getInstList().insertAfter(pi, newInst);

Code and solution taken from here.

like image 31
stanm Avatar answered Oct 19 '22 18:10

stanm