Skip to content

Commit 69e1cc7

Browse files
committed
new runOn method
remove templates unit tests added format updated data structures format
1 parent 5df7d88 commit 69e1cc7

File tree

5 files changed

+341
-2
lines changed

5 files changed

+341
-2
lines changed

llvm/include/llvm/Transforms/IPO/MergeFunctions.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,10 @@
1515
#ifndef LLVM_TRANSFORMS_IPO_MERGEFUNCTIONS_H
1616
#define LLVM_TRANSFORMS_IPO_MERGEFUNCTIONS_H
1717

18+
#include "llvm/IR/Function.h"
1819
#include "llvm/IR/PassManager.h"
20+
#include <map>
21+
#include <set>
1922

2023
namespace llvm {
2124

@@ -25,6 +28,10 @@ class Module;
2528
class MergeFunctionsPass : public PassInfoMixin<MergeFunctionsPass> {
2629
public:
2730
PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM);
31+
32+
static bool runOnModule(Module &M);
33+
static std::pair<bool, std::map<Function *, Function *>>
34+
runOnFunctions(std::set<Function *> &F);
2835
};
2936

3037
} // end namespace llvm

llvm/lib/Transforms/IPO/MergeFunctions.cpp

Lines changed: 61 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,7 @@
123123
#include <algorithm>
124124
#include <cassert>
125125
#include <iterator>
126+
#include <map>
126127
#include <set>
127128
#include <utility>
128129
#include <vector>
@@ -198,6 +199,8 @@ class MergeFunctions {
198199
}
199200

200201
bool runOnModule(Module &M);
202+
bool runOnFunctions(std::set<Function *> &F);
203+
std::map<Function *, Function *> &getDelToNewMap();
201204

202205
private:
203206
// The function comparison operator is provided here so that FunctionNodes do
@@ -298,17 +301,31 @@ class MergeFunctions {
298301
// dangling iterators into FnTree. The invariant that preserves this is that
299302
// there is exactly one mapping F -> FN for each FunctionNode FN in FnTree.
300303
DenseMap<AssertingVH<Function>, FnTreeType::iterator> FNodesInTree;
304+
305+
/// Deleted-New functions mapping
306+
std::map<Function *, Function *> DelToNewMap;
301307
};
302308
} // end anonymous namespace
303309

304310
PreservedAnalyses MergeFunctionsPass::run(Module &M,
305311
ModuleAnalysisManager &AM) {
306-
MergeFunctions MF;
307-
if (!MF.runOnModule(M))
312+
if (!MergeFunctionsPass::runOnModule(M))
308313
return PreservedAnalyses::all();
309314
return PreservedAnalyses::none();
310315
}
311316

317+
bool MergeFunctionsPass::runOnModule(Module &M) {
318+
MergeFunctions MF;
319+
return MF.runOnModule(M);
320+
}
321+
322+
std::pair<bool, std::map<Function *, Function *>>
323+
MergeFunctionsPass::runOnFunctions(std::set<Function *> &F) {
324+
MergeFunctions MF;
325+
bool MergeResult = MF.runOnFunctions(F);
326+
return {MergeResult, MF.getDelToNewMap()};
327+
}
328+
312329
#ifndef NDEBUG
313330
bool MergeFunctions::doFunctionalCheck(std::vector<WeakTrackingVH> &Worklist) {
314331
if (const unsigned Max = NumFunctionsForVerificationCheck) {
@@ -468,6 +485,47 @@ bool MergeFunctions::runOnModule(Module &M) {
468485
return Changed;
469486
}
470487

488+
bool MergeFunctions::runOnFunctions(std::set<Function *> &F) {
489+
bool Changed = false;
490+
std::vector<std::pair<IRHash, Function *>> HashedFuncs;
491+
for (Function *Func : F) {
492+
if (isEligibleForMerging(*Func)) {
493+
HashedFuncs.push_back({StructuralHash(*Func), Func});
494+
}
495+
}
496+
llvm::stable_sort(HashedFuncs, less_first());
497+
auto S = HashedFuncs.begin();
498+
for (auto I = HashedFuncs.begin(), IE = HashedFuncs.end(); I != IE; ++I) {
499+
if ((I != S && std::prev(I)->first == I->first) ||
500+
(std::next(I) != IE && std::next(I)->first == I->first)) {
501+
Deferred.push_back(WeakTrackingVH(I->second));
502+
}
503+
}
504+
do {
505+
std::vector<WeakTrackingVH> Worklist;
506+
Deferred.swap(Worklist);
507+
LLVM_DEBUG(dbgs() << "size of function: " << F.size() << '\n');
508+
LLVM_DEBUG(dbgs() << "size of worklist: " << Worklist.size() << '\n');
509+
for (WeakTrackingVH &I : Worklist) {
510+
if (!I)
511+
continue;
512+
Function *F = cast<Function>(I);
513+
if (!F->isDeclaration() && !F->hasAvailableExternallyLinkage()) {
514+
Changed |= insert(F);
515+
}
516+
}
517+
LLVM_DEBUG(dbgs() << "size of FnTree: " << FnTree.size() << '\n');
518+
} while (!Deferred.empty());
519+
FnTree.clear();
520+
FNodesInTree.clear();
521+
GlobalNumbers.clear();
522+
return Changed;
523+
}
524+
525+
std::map<Function *, Function *> &MergeFunctions::getDelToNewMap() {
526+
return this->DelToNewMap;
527+
}
528+
471529
// Replace direct callers of Old with New.
472530
void MergeFunctions::replaceDirectCallers(Function *Old, Function *New) {
473531
for (Use &U : llvm::make_early_inc_range(Old->uses())) {
@@ -1004,6 +1062,7 @@ bool MergeFunctions::insert(Function *NewFunction) {
10041062

10051063
Function *DeleteF = NewFunction;
10061064
mergeTwoFunctions(OldF.getFunc(), DeleteF);
1065+
this->DelToNewMap.emplace(DeleteF, OldF.getFunc());
10071066
return true;
10081067
}
10091068

llvm/unittests/Transforms/Utils/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ add_llvm_unittest(UtilsTests
2626
LoopUtilsTest.cpp
2727
MemTransferLowering.cpp
2828
ModuleUtilsTest.cpp
29+
MergeFunctionsTest.cpp
2930
ScalarEvolutionExpanderTest.cpp
3031
SizeOptsTest.cpp
3132
SSAUpdaterBulkTest.cpp

0 commit comments

Comments
 (0)