0

私はLLVM最適化モジュールを書いています。結果が気に入らなければ元の関数に戻すことができます。だから私は、次の基本的な構造とModulePassを書いた:CloneFunctionは元の関数をLLVM opt passのクローン1と置き換えます

while(cloneAndTryAgain){ 

    ValueToValueMapTy vmap; 
    Function *F_clone = CloneFunction(F, vmap, true); 

    .... trying out things on F 

    if(cloneAndTryAgain){ //not happy with changes to F 
     //replace F with clone 
     replaceCurrentFunction(F, F_clone); 
     F_clone = NULL; 
    } 
} 

しかし、replaceCurrentFunction(..)を実行した後、私はFを印刷しようが、私はセグメンテーション違反を取得します。クローンと置き換えようとした後、Fに何か問題があります。

replaceCurrentFunction(..)次のようになります。

void replaceCurrentFunction(Function *F, Function *F_clone) { 

    Module *M = F->getParent(); 

    // New function will take the name of the current function. 
    F_clone->takeName(F); 

    // Insert new function right next to current function. 
    M->getFunctionList().insert(F, F_clone); 

    // Erase current function. 
    F->eraseFromParent(); 

    // The new function is now the current function. 
    F = F_clone; 

} 

はここでセグメンテーション違反やスタックトレースです:

Program received signal SIGSEGV, Segmentation fault. 
(anonymous namespace)::SlotTracker::SlotTracker (this=0x7fffffff94b0, F=0x1b) at AsmWriter.cpp:438 
438  mNext(0), fNext(0), mdnNext(0) { 

#0 (anonymous namespace)::SlotTracker::SlotTracker (this=0x7fffffff94b0, F=0x1b) at AsmWriter.cpp:438 
#1 0x00007ffff63c66dc in llvm::Value::print (this=0x6d4a30, ROS=..., AAW=0x0) at AsmWriter.cpp:2092 
#2 0x00007ffff6fb536c in operator<< (V=..., OS=...) at /llvm/include/llvm/Value.h:318 
#4 .... 

答えて

0

うわー、あなたがここに危険なのAPIの束を使用している、といくつかのステートメントでも作っていませんセンス。例えば、void replaceCurrentFunction(Function *F, Function *F_clone)の最後の行には何がありますか?F = F_clone;?呼び出し元の "F"を更新する場合は、この関数をreturn F_cloneで終了し、これをF = replaceCurrentFunction(F, F_clone);と呼びます。実際のLLVM APIの場合

、正しい順序は次のとおりです。

  1. クローンと古い機能のすべての使用を置き換えます F->replaceAllUsesWith(F_clone)
  2. 保存に名前:std::string Name = F->getName()
  3. Fを削除します。F->eraseFromParent()
  4. クローンの名前を変更します。F_clone->setName(Name)
+0

Ieeee私は別のクローンを作成するためにそれを使用するので、私はF = F_cloneについてF = F_clone – mohsaied

+0

を 'F = F_clone'としています。私はそれを正しく設定する関数へのポインタ参照を渡す必要があります。ですから、私の新しい関数プロトタイプは 'replaceCurrentFunction(Function *&F、Function *&F_clone)'になりました。これは、Fが私の外側のループの正しいものを指し示しているところで、そこで私はそれをクローンして再試行します。 – mohsaied

+0

Fがポインタ参照の場合、それは意味があります。しかしこれは素晴らしいことではありません。コールサイトで代入を行う代わりに、ポインタを返す必要があります。 私が説明した残りのステップはまだ有効です(あなたの質問が正しく解決されている場合は回答を受け入れるか、そうでない場合は改善する方法を教えてください)。 – Joky

関連する問題