Index: llvm/lib/Analysis/CallGraph.cpp =================================================================== --- llvm/lib/Analysis/CallGraph.cpp +++ llvm/lib/Analysis/CallGraph.cpp @@ -281,13 +281,37 @@ I->second = NewNode; NewNode->AddRef(); - // Refresh callback references. - forEachCallbackFunction(Call, [=](Function *CB) { - removeOneAbstractEdgeTo(CG->getOrInsertFunction(CB)); + // Refresh callback references. Do not resize CalledFunctions if the + // number of callbacks is the same for new and old call sites. + SmallVector OldCBs; + SmallVector NewCBs; + forEachCallbackFunction(Call, [this, &OldCBs](Function *CB) { + OldCBs.push_back(CG->getOrInsertFunction(CB)); }); - forEachCallbackFunction(NewCall, [=](Function *CB) { - addCalledFunction(nullptr, CG->getOrInsertFunction(CB)); + forEachCallbackFunction(NewCall, [this, &NewCBs](Function *CB) { + NewCBs.push_back(CG->getOrInsertFunction(CB)); }); + if (OldCBs.size() == NewCBs.size()) { + for (unsigned I = 0; I < OldCBs.size(); I++) { + CallGraphNode *OldNode = OldCBs[I]; + CallGraphNode *NewNode = NewCBs[I]; + for (auto I = CalledFunctions.begin();; ++I) { + assert(I != CalledFunctions.end() && + "Cannot find callsite to update!"); + if (!I->first && I->second == OldNode) { + I->second = NewNode; + OldNode->DropRef(); + NewNode->AddRef(); + break; + } + } + } + } else { + for (auto *CGN : OldCBs) + removeOneAbstractEdgeTo(CGN); + for (auto *CGN : NewCBs) + addCalledFunction(nullptr, CGN); + } return; } }