50#define DEBUG_TYPE "split-module"
58bool compareClusters(
const std::pair<unsigned, unsigned> &
A,
59 const std::pair<unsigned, unsigned> &
B) {
60 if (
A.second ||
B.second)
61 return A.second >
B.second;
62 return A.first >
B.first;
65using BalancingQueueType =
66 std::priority_queue<std::pair<unsigned, unsigned>,
67 std::vector<std::pair<unsigned, unsigned>>,
68 decltype(compareClusters) *>;
78 GVtoClusterMap.unionSets(GV,
F);
80 GVtoClusterMap.unionSets(GV, GVU);
89 for (
const auto *U : V->users()) {
92 while (!Worklist.
empty()) {
107 GO = GI->getResolverFunction();
122 ClusterMapType GVtoClusterMap;
123 ComdatMembersType ComdatMembers;
125 auto recordGVSet = [&GVtoClusterMap, &ComdatMembers](
GlobalValue &GV) {
126 if (GV.isDeclaration())
135 if (
const Comdat *
C = GV.getComdat()) {
136 auto &Member = ComdatMembers[
C];
138 GVtoClusterMap.unionSets(Member, &GV);
147 GVtoClusterMap.unionSets(&GV, Root);
158 if (GV.hasLocalLinkage())
169 BalancingQueueType BalancingQueue(compareClusters);
171 for (
unsigned i = 0; i <
N; ++i)
172 BalancingQueue.push(std::make_pair(i, 0));
178 for (
const auto &
C : GVtoClusterMap) {
182 unsigned CurrentClusterID = BalancingQueue.top().first;
183 unsigned CurrentClusterSize = BalancingQueue.top().second;
184 BalancingQueue.pop();
186 LLVM_DEBUG(
dbgs() <<
"Root[" << CurrentClusterID <<
"] cluster_size("
187 << std::distance(GVtoClusterMap.member_begin(*
C),
188 GVtoClusterMap.member_end())
189 <<
") ----> " <<
C->getData()->getName() <<
"\n");
191 for (ClusterMapType::member_iterator
MI = GVtoClusterMap.findLeader(*
C);
192 MI != GVtoClusterMap.member_end(); ++
MI) {
193 if (!Visited.
insert(*MI).second)
196 << ((*MI)->hasLocalLinkage() ?
" l " :
" e ") <<
"\n");
198 ClusterIDMap[*
MI] = CurrentClusterID;
199 CurrentClusterSize++;
202 BalancingQueue.push(std::make_pair(CurrentClusterID, CurrentClusterSize));
224 return (R[0] | (R[1] << 8)) %
N ==
I;
229 function_ref<
void(std::unique_ptr<Module> MPart)> ModuleCallback,
230 bool PreserveLocals,
bool RoundRobin) {
231 if (!PreserveLocals) {
244 ClusterIDMapType ClusterIDMap;
255 for (
const auto &
F : M.functions()) {
256 if (
F.isDeclaration() ||
259 auto It = ClusterIDMap.find(&
F);
260 if (It == ClusterIDMap.end())
263 ++ModuleFunctionCount[It->second];
265 BalancingQueueType BalancingQueue(compareClusters);
266 for (
unsigned I = 0;
I <
N; ++
I) {
267 if (
auto It = ModuleFunctionCount.
find(
I);
268 It != ModuleFunctionCount.
end())
269 BalancingQueue.push(*It);
271 BalancingQueue.push({
I, 0});
273 for (
const auto *
const F : UnmappedFunctions) {
274 const unsigned I = BalancingQueue.top().first;
275 const unsigned Count = BalancingQueue.top().second;
276 BalancingQueue.pop();
277 ClusterIDMap.insert({
F,
I});
278 BalancingQueue.push({
I,
Count + 1});
285 for (
unsigned I = 0;
I <
N; ++
I) {
287 std::unique_ptr<Module> MPart(
289 if (
auto It = ClusterIDMap.find(GV); It != ClusterIDMap.end())
290 return It->second ==
I;
295 MPart->removeModuleInlineAsm();
296 ModuleCallback(std::move(MPart));
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
This file contains the declarations for the subclasses of Constant, which represent the different fla...
This file defines the DenseMap class.
Generic implementation of equivalence classes through the use Tarjan's efficient union-find algorithm...
Module.h This file contains the declarations for the Module class.
This file defines the SmallPtrSet class.
This file defines the SmallVector class.
static bool isInPartition(const GlobalValue *GV, unsigned I, unsigned N)
static void addNonConstUser(ClusterMapType &GVtoClusterMap, const GlobalValue *GV, const User *U)
static void findPartitions(Module &M, ClusterIDMapType &ClusterIDMap, unsigned N)
static const GlobalObject * getGVPartitioningRoot(const GlobalValue *GV)
static void addAllGlobalValueUsers(ClusterMapType &GVtoClusterMap, const GlobalValue *GV, const Value *V)
LLVM Basic Block Representation.
The address of a basic block.
static LLVM_ABI BlockAddress * lookup(const BasicBlock *BB)
Lookup an existing BlockAddress constant for the given BasicBlock.
LLVM_ABI bool isConstantUsed() const
Return true if the constant has users other than constant expressions and other dangling things.
iterator find(const_arg_type_t< KeyT > Val)
This represents a collection of equivalence classes and supports three efficient operations: insert a...
LLVM_ABI const Comdat * getComdat() const
LLVM_ABI const GlobalObject * getAliaseeObject() const
@ ExternalLinkage
Externally visible function.
A Module instance is used to store all the information related to an LLVM module.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
void append(ItTy in_start, ItTy in_end)
Add the specified range to the end of the SmallVector.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Represent a constant reference to a string, i.e.
LLVM Value Representation.
user_iterator user_begin()
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
An efficient, type-erasing, non-owning reference to a callable.
This file contains the declaration of the Comdat class, which represents a single COMDAT in LLVM.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
This is an optimization pass for GlobalISel generic memory operations.
UnaryFunction for_each(R &&Range, UnaryFunction F)
Provide wrappers to std::for_each which take ranges instead of having to pass begin/end explicitly.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
auto dyn_cast_or_null(const Y &Val)
LLVM_ABI void SplitModule(Module &M, unsigned N, function_ref< void(std::unique_ptr< Module > MPart)> ModuleCallback, bool PreserveLocals=false, bool RoundRobin=false)
Splits the module M into N linkable partitions.
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
LLVM_ABI void nameUnnamedGlobalValue(GlobalValue &GV)
Assign a stable name to GV if it is unnamed, so that it is named consistently across the split partit...
LLVM_ABI void externalizeGlobal(GlobalValue &GV)
If GV has local linkage, promote it to external + hidden visibility so it can be referenced across mo...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Count
ValueMap< const Value *, WeakTrackingVH > ValueToValueMapTy
LLVM_ABI std::unique_ptr< Module > CloneModule(const Module &M)
Return an exact copy of the specified module.