<div dir="ltr"><div>Hi,</div><div><br></div><div>I understood that I have been incrementing that global variable the whole time, but printing wrong stuff. I added missing load of global variable and now I am passing the loaded value to printf function.</div><div>Code looks like this and works fine:<br></div><div>
<pre class="gmail-lang-cpp gmail-prettyprint gmail-prettyprinted"><code><span class="gmail-typ">Instruction</span><span class="gmail-pun">*</span><span class="gmail-pln"> </span><span class="gmail-typ">InstructionVisitor</span><span class="gmail-pun">::</span><span class="gmail-pln">getGlobalValue</span><span class="gmail-pun">(</span><span class="gmail-typ">Instruction</span><span class="gmail-pun">*</span><span class="gmail-pln"> I</span><span class="gmail-pun">,</span><span class="gmail-pln"> </span><span class="gmail-typ">StringRef</span><span class="gmail-pln"> </span><span class="gmail-typ">Name</span><span class="gmail-pun">)</span><span class="gmail-pln"> </span><span class="gmail-pun">{</span><span class="gmail-pln">
    </span><span class="gmail-typ">IRBuilder</span><span class="gmail-pun"><></span><span class="gmail-pln"> </span><span class="gmail-typ">Builder</span><span class="gmail-pun">(</span><span class="gmail-pln">I</span><span class="gmail-pun">-></span><span class="gmail-pln">getContext</span><span class="gmail-pun">());</span><span class="gmail-pln">
    </span><span class="gmail-typ">Builder</span><span class="gmail-pun">.</span><span class="gmail-typ">SetInsertPoint</span><span class="gmail-pun">(</span><span class="gmail-pln">I</span><span class="gmail-pun">-></span><span class="gmail-pln">getNextNode</span><span class="gmail-pun">());</span><span class="gmail-pln">
    </span><span class="gmail-typ">GlobalVariable</span><span class="gmail-pun">*</span><span class="gmail-pln"> key </span><span class="gmail-pun">=</span><span class="gmail-pln"> I</span><span class="gmail-pun">-></span><span class="gmail-pln">getModule</span><span class="gmail-pun">()-></span><span class="gmail-pln">getNamedGlobal</span><span class="gmail-pun">(</span><span class="gmail-typ">Name</span><span class="gmail-pun">);</span><span class="gmail-pln">
    </span><span class="gmail-kwd">if</span><span class="gmail-pln"> </span><span class="gmail-pun">(</span><span class="gmail-pln">key</span><span class="gmail-pun">)</span><span class="gmail-pln"> </span><span class="gmail-pun">{</span><span class="gmail-pln">
        </span><span class="gmail-typ">LoadInst</span><span class="gmail-pun">*</span><span class="gmail-pln"> load </span><span class="gmail-pun">=</span><span class="gmail-pln"> </span><span class="gmail-typ">Builder</span><span class="gmail-pun">.</span><span class="gmail-typ">CreateLoad</span><span class="gmail-pun">(</span><span class="gmail-pln">key</span><span class="gmail-pun">);</span><span class="gmail-pln">
        </span><span class="gmail-kwd">return</span><span class="gmail-pln"> load</span><span class="gmail-pun">;</span><span class="gmail-pln">
    </span><span class="gmail-pun">}</span><span class="gmail-pln">
    </span><span class="gmail-kwd">return</span><span class="gmail-pln"> </span><span class="gmail-kwd">nullptr</span><span class="gmail-pun">;</span><span class="gmail-pln">
</span><span class="gmail-pun">}</span><span class="gmail-pln">

</span><span class="gmail-kwd">void</span><span class="gmail-pln"> </span><span class="gmail-typ">InstructionVisitor</span><span class="gmail-pun">::</span><span class="gmail-pln">visitCallInst</span><span class="gmail-pun">(</span><span class="gmail-typ">CallInst</span><span class="gmail-pln"> </span><span class="gmail-pun">&</span><span class="gmail-pln">CI</span><span class="gmail-pun">)</span><span class="gmail-pln"> </span><span class="gmail-pun">{</span><span class="gmail-pln">
    </span><span class="gmail-kwd">if</span><span class="gmail-pln"> </span><span class="gmail-pun">(</span><span class="gmail-pln">isAllocationFn</span><span class="gmail-pun">(&</span><span class="gmail-pln">CI</span><span class="gmail-pun">,</span><span class="gmail-pln"> </span><span class="gmail-pun">&</span><span class="gmail-pln">TLI</span><span class="gmail-pun">))</span><span class="gmail-pln"> </span><span class="gmail-pun">{</span><span class="gmail-pln">
        </span><span class="gmail-typ">Value</span><span class="gmail-pun">*</span><span class="gmail-pln"> allocatedAddress </span><span class="gmail-pun">=</span><span class="gmail-pln"> </span><span class="gmail-pun">&</span><span class="gmail-pln">CI</span><span class="gmail-pun">;</span><span class="gmail-pln">
        </span><span class="gmail-typ">Instruction</span><span class="gmail-pun">*</span><span class="gmail-pln"> I </span><span class="gmail-pun">=</span><span class="gmail-pln"> </span><span class="gmail-pun">&</span><span class="gmail-pln">CI</span><span class="gmail-pun">;</span><span class="gmail-pln">
        </span><span class="gmail-typ">Value</span><span class="gmail-pun">*</span><span class="gmail-pln"> allocatedSize </span><span class="gmail-pun">=</span><span class="gmail-pln"> I</span><span class="gmail-pun">-></span><span class="gmail-pln">getOperand</span><span class="gmail-pun">(</span><span class="gmail-lit">0</span><span class="gmail-pun">);</span><span class="gmail-pln">
        </span><span class="gmail-typ">Instruction</span><span class="gmail-pun">*</span><span class="gmail-pln"> next </span><span class="gmail-pun">=</span><span class="gmail-pln"> incrementGlobalKey</span><span class="gmail-pun">(</span><span class="gmail-pln">I</span><span class="gmail-pun">,</span><span class="gmail-pln"> allocatedAddress</span><span class="gmail-pun">,</span><span class="gmail-pln"> allocatedSize</span><span class="gmail-pun">);</span><span class="gmail-pln">
        </span><span class="gmail-typ">Instruction</span><span class="gmail-pun">*</span><span class="gmail-pln"> loadKey </span><span class="gmail-pun">=</span><span class="gmail-pln"> getGlobalValue</span><span class="gmail-pun">(</span><span class="gmail-pln">next</span><span class="gmail-pun">,</span><span class="gmail-pln"> </span><span class="gmail-str">"globalKey"</span><span class="gmail-pun">);</span><span class="gmail-com"></span><span class="gmail-pln">

        </span><span class="gmail-kwd">const</span><span class="gmail-pln"> </span><span class="gmail-kwd">char</span><span class="gmail-pun">*</span><span class="gmail-pln"> message </span><span class="gmail-pun">=</span><span class="gmail-pln"> </span><span class="gmail-str">"Allocated address: 0x%p, size: %d, key: %lld\n"</span><span class="gmail-pun">;</span><span class="gmail-pln">
        next </span><span class="gmail-pun">=</span><span class="gmail-pln"> print</span><span class="gmail-pun">(</span><span class="gmail-pln">loadKey</span><span class="gmail-pun">,</span><span class="gmail-pln"> message</span><span class="gmail-pun">,</span><span class="gmail-pln"> allocatedAddress</span><span class="gmail-pun">,</span><span class="gmail-pln"> allocatedSize</span><span class="gmail-pun">,</span><span class="gmail-pln"> loadKey</span><span class="gmail-pun">);</span><span class="gmail-pln">
    </span><span class="gmail-pun">}</span><span class="gmail-pln">
</span><span class="gmail-pun">}<br><br></span></code></pre><pre class="gmail-lang-cpp gmail-prettyprint gmail-prettyprinted"><code><span class="gmail-pun"><font face="arial,sans-serif">Thank you,<br>Emma Luciano<br></font></span></code></pre>

</div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">śr., 3 cze 2020 o 22:18 Johannes Doerfert <<a href="mailto:johannesdoerfert@gmail.com">johannesdoerfert@gmail.com</a>> napisał(a):<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
  
    
  
  <div>
    <p><font face="Hack Nerd Font Mono">Right.</font></p>
    <p><font face="Hack Nerd Font Mono"><br>
      </font></p>
    <p><font face="Hack Nerd Font Mono">Maybe I can put this a bit
        differently:<br>
      </font></p>
    <p><font face="Hack Nerd Font Mono">A `llvm::GlobalVariable` is
        *not* the source variable but a pointer to the storage location
        of the source variable.</font></p>
    <p>This is the same for an `llvm::AllocaInst` that represents a
      local variable.</p>
    <p> Using a source variable means reading the `llvm::GlobalVariable`
      (or `llvm::AllocaInst`) that models the memory allocated for the
      source variable.</p>
    <p> Changing the variable corresponds to a write.<br>
    </p>
    <p><br>
    </p>
    <p>Hope this helps :)<br>
    </p>
    <p><br>
    </p>
    <p><br>
    </p>
    <div>On 6/3/20 1:56 PM, David Blaikie via
      llvm-dev wrote:<br>
    </div>
    <blockquote type="cite">
      <pre>I'm with Eli on this "GlobalVariable" is not the actual global
variable in memory - it's the IR representation of the global variable
before it is compiled to machine code & allocated in the running
process - it always has the same value/isn't affected by the execution
of loads and stores at runtime.

On Wed, Jun 3, 2020 at 2:53 AM Emma Luciano via llvm-dev
<a href="mailto:llvm-dev@lists.llvm.org" target="_blank"><llvm-dev@lists.llvm.org></a> wrote:
</pre>
      <blockquote type="cite">
        <pre>I don't think it's the same problem as you described. By printing I meant calling printf function and passing my global variable as one of the arguments.

My code:

Instruction* InstructionVisitor::incrementGlobalKey(Instruction* I) {
IRBuilder<> Builder(I->getContext());
Builder.SetInsertPoint(I->getNextNode());

GlobalVariable* key = I->getModule()->getNamedGlobal("globalKey");

if (key) {
LoadInst* load = Builder.CreateLoad(key);
Value* inc = Builder.CreateAdd(load, Builder.getInt64(1));
StoreInst* store = Builder.CreateStore(inc, key);
return store;
}
return I;
}

Instruction* InstructionVisitor::print(Instruction* I, const char* text, Value* arg1, Value* arg2, Value* arg3, Value* arg4) {
Function* printfFn = I->getModule()->getFunction("printf");
if (printfFn) {
IRBuilder<> Builder(I->getContext());
Builder.SetInsertPoint(I->getNextNode());
Value* convertedText = Builder.CreateGlobalStringPtr(text);

std::vector <Value *> params;
params.push_back(convertedText);
if (arg1)
params.push_back(arg1);
if (arg2)
params.push_back(arg2);
if (arg3)
params.push_back(arg3);
if (arg4)
params.push_back(arg4);

return Builder.CreateCall(printfFn, params);
}
return I;
}

void InstructionVisitor::visitCallInst(CallInst &CI) {
if (isAllocationFn(&CI, &TLI)) {
Value* allocatedAddress = &CI;
Instruction* I = &CI;
Value* allocatedSize = I->getOperand(0);
Instruction* next = incrementGlobalKey(I);
GlobalVariable* key = I->getModule()->getNamedGlobal("globalKey");
const char* message = "Allocated address: 0x%p, size: %d, key: %lld\n";
print(next, message, allocatedAddress, allocatedSize, key->getOperand(0));
}
}

Code that I'm executing (source code) is:
int main()
{
char* buffer;
int size = 101;
buffer = new char[size];
printf("CHECK address: 0x%p, size: %d\n", buffer, size);
TestClass* test = new TestClass(1, 2);
printf("(CHECK address: 0x%p, size: %llu\n", test, sizeof(TestClass));

delete buffer;
delete test;
}

And program output after instrumentation:

Allocated address: 0x000001CD326C1B20, size: 101, key: 0
CHECK address: 0x000001CD326C1B20, size: 101
Allocated address: 0x000001CD326C1B90, size: 8, key: 0
CHECK address: 0x000001CD326C1B90, size: 8

Regards,
Emma Luciano

śr., 3 cze 2020 o 11:21 Eli Friedman <a href="mailto:efriedma@quicinc.com" target="_blank"><efriedma@quicinc.com></a> napisał(a):
</pre>
        <blockquote type="cite">
          <pre>Suppose I have the following program:



$ cat test.c

int a = 0;

int main() { a = 1; };



Then I compile and run it:

$ clang test.c

$ ./a.out



Then I print the contents of test.c again:



$ cat test.c

int a = 0;

int main() { a = 1; }



Why does it say “int a = 0;”?  The program set it to 1, no?



As far as I can tell, this is equivalent to your question… except it’s less obvious because the “source code” is an LLVM IR module in memory.



Maybe you’re looking for ExecutionSession::lookup?  The same way the tutorial computes the address of “main”, you can compute the runtime address of any other externally visible symbol.



See also <a href="https://llvm.org/docs/ORCv2.html" target="_blank">https://llvm.org/docs/ORCv2.html</a> , <a href="https://www.youtube.com/watch?v=hILdR8XRvdQ" target="_blank">https://www.youtube.com/watch?v=hILdR8XRvdQ</a> .



-Eli



From: llvm-dev <a href="mailto:llvm-dev-bounces@lists.llvm.org" target="_blank"><llvm-dev-bounces@lists.llvm.org></a> On Behalf Of Emma Luciano via llvm-dev
Sent: Wednesday, June 3, 2020 1:35 AM
To: <a href="mailto:llvm-dev@lists.llvm.org" target="_blank">llvm-dev@lists.llvm.org</a>
Subject: [EXT] [llvm-dev] Fwd: I cannot change value of global variable in LLVM IR using IRBuilder



Hi Everyone,

I'm quite new to LLVM and I want to update value of global variable in LLVM IR. I created new global variable in ModulePass:

bool runOnModule(llvm::Module &M) {

    IRBuilder<> Builder(M.getContext());

    Instruction *I = &*inst_begin(M.getFunction("main"));

    Builder.SetInsertPoint(I);

    M.getOrInsertGlobal("globalKey", Builder.getInt64Ty());

    GlobalVariable* gVar = M.getNamedGlobal("globalKey");

    gVar->setLinkage(GlobalValue::InternalLinkage);

    gVar->setAlignment(Align(8));

    gVar->setInitializer(Builder.getInt64(0));

    gVar->setConstant(false);



    for (Function &F : M.functions()) {

        InstructionVisitor visitor(DL, getAnalysis<TargetLibraryInfoWrapperPass>().getTLI(F));

        for (Instruction &I : instructions(F)) {

            visitor.visit(I);

        }

    }

    return true;

}

Later in InstructionVisitor I try to update it like that:

IRBuilder<> Builder(I->getContext());

Builder.SetInsertPoint(I->getNextNode());



GlobalVariable* key = I->getModule()->getNamedGlobal("globalKey");



if (key) {

    LoadInst* load = Builder.CreateLoad(key);

    Value* inc = Builder.CreateAdd(load, Builder.getInt64(1));

    StoreInst* store = Builder.CreateStore(inc, key);

}

I print that global variable during execution of instrumented code. I access it's value by key->getOperand(0), but it's unchanged. I'm using ORC JIT based on this tutorial: <a href="https://llvm.org/docs/tutorial/BuildingAJIT2.html" target="_blank">https://llvm.org/docs/tutorial/BuildingAJIT2.html</a> and I run ModulePass from optimizeModule function from this tutorial.

In IR it looks like that:

  %2 = load i64, i64* @globalKey

  %3 = add i64 %2, 1

  store i64 %3, i64* @globalKey

I tried updating value of global variable, which was present in source code that I'm instrumenting. It didn't work either.

I created corresponding stackoverflow topic: <a href="https://stackoverflow.com/questions/62142574/how-can-i-update-global-variable-value-in-llvm-ir-using-irbuilder?fbclid=IwAR2X7uGhUjm_SN2UcxWYqaRQW2-cs6iPbMx2_tbKubeyYUkZ_pS6rkFfY9I" target="_blank">https://stackoverflow.com/questions/62142574/how-can-i-update-global-variable-value-in-llvm-ir-using-irbuilder?fbclid=IwAR2X7uGhUjm_SN2UcxWYqaRQW2-cs6iPbMx2_tbKubeyYUkZ_pS6rkFfY9I</a>

I will be really grateful for help.

Regards,

Emma Luciano
</pre>
        </blockquote>
        <pre>_______________________________________________
LLVM Developers mailing list
<a href="mailto:llvm-dev@lists.llvm.org" target="_blank">llvm-dev@lists.llvm.org</a>
<a href="https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev" target="_blank">https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev</a>
</pre>
      </blockquote>
      <pre>_______________________________________________
LLVM Developers mailing list
<a href="mailto:llvm-dev@lists.llvm.org" target="_blank">llvm-dev@lists.llvm.org</a>
<a href="https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev" target="_blank">https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev</a>
</pre>
    </blockquote>
  </div>

</blockquote></div>