LLVM 24.0.0git
GlobalMergeFunctions.cpp
Go to the documentation of this file.
1//===---- GlobalMergeFunctions.cpp - Global merge functions -------*- C++ -===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This pass implements the global merge function pass.
10//
11//===----------------------------------------------------------------------===//
12
14#include "llvm/ADT/Statistic.h"
18#include "llvm/CodeGen/Passes.h"
19#include "llvm/IR/IRBuilder.h"
24
25#define DEBUG_TYPE "global-merge-func"
26
27using namespace llvm;
28using namespace llvm::support;
29
31 "disable-cgdata-for-merging", cl::Hidden,
32 cl::desc("Disable codegen data for function merging. Local "
33 "merging is still enabled within a module."),
34 cl::init(false));
35
36STATISTIC(NumMergedFunctions,
37 "Number of functions that are actually merged using function hash");
38STATISTIC(NumAnalyzedModues, "Number of modules that are analyzed");
39STATISTIC(NumAnalyzedFunctions, "Number of functions that are analyzed");
40STATISTIC(NumEligibleFunctions, "Number of functions that are eligible");
41
42/// Returns true if the \OpIdx operand of \p CI is the callee operand.
43static bool isCalleeOperand(const CallBase *CI, unsigned OpIdx) {
44 return &CI->getCalledOperandUse() == &CI->getOperandUse(OpIdx);
45}
46
47static bool canParameterizeCallOperand(const CallBase *CI, unsigned OpIdx) {
48 if (CI->isInlineAsm())
49 return false;
50 Function *Callee = CI->getCalledOperand()
53 : nullptr;
54 if (Callee) {
55 if (Callee->isIntrinsic())
56 return false;
57 auto Name = Callee->getName();
58 // objc_msgSend stubs must be called, and can't have their address taken.
59 if (Name.starts_with("objc_msgSend$"))
60 return false;
61 // Calls to dtrace probes must generate unique patchpoints.
62 if (Name.starts_with("__dtrace"))
63 return false;
64 }
65 if (isCalleeOperand(CI, OpIdx)) {
66 // The operand is the callee and it has already been signed. Ignore this
67 // because we cannot add another ptrauth bundle to the call instruction.
68 if (CI->getOperandBundle(LLVMContext::OB_ptrauth).has_value())
69 return false;
70 } else {
71 // The target of the arc-attached call must be a constant and cannot be
72 // parameterized.
74 OpIdx))
75 return false;
76 }
77 return true;
78}
79
80/// Returns true if function \p F is eligible for merging.
82 if (F->isDeclaration())
83 return false;
84
85 if (F->hasFnAttribute(llvm::Attribute::NoMerge) ||
86 F->hasFnAttribute(llvm::Attribute::AlwaysInline))
87 return false;
88
89 if (F->hasAvailableExternallyLinkage())
90 return false;
91
92 if (F->getFunctionType()->isVarArg())
93 return false;
94
95 if (F->getCallingConv() == CallingConv::SwiftTail)
96 return false;
97
98 // Unnamed functions are skipped for simplicity.
99 if (!F->hasName())
100 return false;
101
102 // If function contains callsites with musttail, if we merge
103 // it, the merged function will have the musttail callsite, but
104 // the number of parameters can change, thus the parameter count
105 // of the callsite will mismatch with the function itself.
106 for (const BasicBlock &BB : *F) {
107 for (const Instruction &I : BB) {
108 const auto *CB = dyn_cast<CallBase>(&I);
109 if (CB && CB->isMustTailCall())
110 return false;
111 }
112 }
113
114 return true;
115}
116
118 switch (I->getOpcode()) {
119 case Instruction::Load:
120 case Instruction::Store:
121 case Instruction::Call:
122 case Instruction::Invoke:
123 return true;
124 default:
125 return false;
126 }
127}
128
129// This function takes an instruction, \p I, and an operand index, \p OpIdx.
130// It returns true if the operand should be ignored in the hash computation.
131// If \p OpIdx is out of range based on the other instruction context, it cannot
132// be ignored.
133static bool ignoreOp(const Instruction *I, unsigned OpIdx) {
134 if (OpIdx >= I->getNumOperands())
135 return false;
136
138 return false;
139
140 if (!isa<Constant>(I->getOperand(OpIdx)))
141 return false;
142
143 if (const auto *CI = dyn_cast<CallBase>(I))
144 return canParameterizeCallOperand(CI, OpIdx);
145
146 return true;
147}
148
150 // Globals with local linkage are qualified with their module's source file
151 // name so that same-named locals in different modules are not mistaken for
152 // identical operands when the merged map is finalized across modules.
154 /*SourceQualifyLocalGlobals=*/true);
155}
156
158 ++NumAnalyzedModues;
159 for (Function &Func : M) {
160 ++NumAnalyzedFunctions;
161 if (isEligibleFunction(&Func)) {
162 ++NumEligibleFunctions;
163
164 auto FI = hashFunction(Func);
165
166 // Convert the operand map to a vector for a serialization-friendly
167 // format.
168 IndexOperandHashVecType IndexOperandHashes;
169 for (auto &Pair : *FI.IndexOperandHashMap)
170 IndexOperandHashes.emplace_back(Pair);
171
172 StableFunction SF(FI.FunctionHash, get_stable_name(Func.getName()).str(),
173 M.getModuleIdentifier(), FI.IndexInstruction->size(),
174 std::move(IndexOperandHashes));
175
176 LocalFunctionMap->insert(SF);
177 }
178 }
179}
180
181/// Tuple to hold function info to process merging.
190
191// Given the func info, and the parameterized locations, create and return
192// a new merged function by replacing the original constants with the new
193// parameters.
195 ArrayRef<Type *> ConstParamTypes,
196 const ParamLocsVecTy &ParamLocsVec) {
197 // Synthesize a new merged function name by appending ".Tgm" to the root
198 // function's name.
199 auto *MergedFunc = FI.F;
200 std::string NewFunctionName =
202 auto *M = MergedFunc->getParent();
203 assert(!M->getFunction(NewFunctionName));
204
205 FunctionType *OrigTy = MergedFunc->getFunctionType();
206 // Get the original params' types.
207 SmallVector<Type *> ParamTypes(OrigTy->param_begin(), OrigTy->param_end());
208 // Append const parameter types that are passed in.
209 ParamTypes.append(ConstParamTypes.begin(), ConstParamTypes.end());
210 FunctionType *FuncType = FunctionType::get(OrigTy->getReturnType(),
211 ParamTypes, /*isVarArg=*/false);
212
213 // Declare a new function
214 Function *NewFunction =
215 Function::Create(FuncType, MergedFunc->getLinkage(), NewFunctionName);
216 if (auto *SP = MergedFunc->getSubprogram())
217 NewFunction->setSubprogram(SP);
218 NewFunction->copyAttributesFrom(MergedFunc);
219 // Preserve entry count for the merged function. Branch weights for blocks
220 // are automatically preserved via splice() which moves the basic blocks.
221 if (auto EC = MergedFunc->getEntryCount())
222 NewFunction->setEntryCount(*EC);
224
226 NewFunction->addFnAttr(Attribute::NoInline);
227
228 // Add the new function before the root function.
229 M->getFunctionList().insert(MergedFunc->getIterator(), NewFunction);
230
231 // Move the body of MergedFunc into the NewFunction.
232 NewFunction->splice(NewFunction->begin(), MergedFunc);
233
234 // Update the original args by the new args.
235 auto NewArgIter = NewFunction->arg_begin();
236 for (Argument &OrigArg : MergedFunc->args()) {
237 Argument &NewArg = *NewArgIter++;
238 OrigArg.replaceAllUsesWith(&NewArg);
239 }
240
241 // Replace the original Constants by the new args.
242 unsigned NumOrigArgs = MergedFunc->arg_size();
243 for (unsigned ParamIdx = 0; ParamIdx < ParamLocsVec.size(); ++ParamIdx) {
244 Argument *NewArg = NewFunction->getArg(NumOrigArgs + ParamIdx);
245 for (auto [InstIndex, OpndIndex] : ParamLocsVec[ParamIdx]) {
246 auto *Inst = FI.IndexInstruction->lookup(InstIndex);
247 auto *OrigC = Inst->getOperand(OpndIndex);
248 if (OrigC->getType() != NewArg->getType()) {
249 IRBuilder<> Builder(Inst->getIterator());
250 Inst->setOperand(OpndIndex,
251 Builder.CreateAggregateCast(NewArg, OrigC->getType()));
252 } else {
253 Inst->setOperand(OpndIndex, NewArg);
254 }
255 }
256 }
257
258 return NewFunction;
259}
260
261// Given the original function (Thunk) and the merged function (ToFunc), create
262// a thunk to the merged function.
264 Function *ToFunc) {
265 auto *Thunk = FI.F;
266
267 assert(Thunk->arg_size() + Params.size() ==
268 ToFunc->getFunctionType()->getNumParams());
269
270 // Save entry count before dropping references (which clears metadata).
271 auto EC = Thunk->getEntryCount();
272
273 Thunk->dropAllReferences();
274
275 BasicBlock *BB = BasicBlock::Create(Thunk->getContext(), "", Thunk);
276 IRBuilder<> Builder(BB);
277
279 unsigned ParamIdx = 0;
280 FunctionType *ToFuncTy = ToFunc->getFunctionType();
281
282 // Add arguments which are passed through Thunk.
283 for (Argument &AI : Thunk->args()) {
284 Args.push_back(
285 Builder.CreateAggregateCast(&AI, ToFuncTy->getParamType(ParamIdx)));
286 ++ParamIdx;
287 }
288
289 // Add new arguments defined by Params.
290 for (auto *Param : Params) {
291 assert(ParamIdx < ToFuncTy->getNumParams());
292 Args.push_back(
293 Builder.CreateAggregateCast(Param, ToFuncTy->getParamType(ParamIdx)));
294 ++ParamIdx;
295 }
296
297 CallInst *CI = Builder.CreateCall(ToFunc, Args);
298 bool isSwiftTailCall = ToFunc->getCallingConv() == CallingConv::SwiftTail &&
299 Thunk->getCallingConv() == CallingConv::SwiftTail;
302 CI->setCallingConv(ToFunc->getCallingConv());
303 CI->setAttributes(ToFunc->getAttributes());
304 if (Thunk->getReturnType()->isVoidTy())
305 Builder.CreateRetVoid();
306 else
307 Builder.CreateRet(Builder.CreateAggregateCast(CI, Thunk->getReturnType()));
308
309 // Restore the thunk's original entry count.
310 if (EC)
311 Thunk->setEntryCount(*EC);
312}
313
314// Check if the old merged/optimized IndexOperandHashMap is compatible with
315// the current IndexOperandHashMap. An operand hash may not be stable across
316// different builds due to varying modules combined. To address this, we relax
317// the hash check condition by comparing Const hash patterns instead of absolute
318// hash values. For example, let's assume we have three Consts located at idx1,
319// idx3, and idx6, where their corresponding hashes are hash1, hash2, and hash1
320// in the old merged map below:
321// Old (Merged): [(idx1, hash1), (idx3, hash2), (idx6, hash1)]
322// Current: [(idx1, hash1'), (idx3, hash2'), (idx6, hash1')]
323// If the current function also has three Consts in the same locations,
324// with hash sequences hash1', hash2', and hash1' where the first and third
325// are the same as the old hash sequences, we consider them matched.
327 const DenseMap<IndexPair, stable_hash> &OldInstOpndIndexToConstHash,
328 const DenseMap<IndexPair, stable_hash> &CurrInstOpndIndexToConstHash) {
329
330 DenseMap<stable_hash, stable_hash> OldHashToCurrHash;
331 for (const auto &[Index, OldHash] : OldInstOpndIndexToConstHash) {
332 auto It = CurrInstOpndIndexToConstHash.find(Index);
333 if (It == CurrInstOpndIndexToConstHash.end())
334 return false;
335
336 auto CurrHash = It->second;
337 auto J = OldHashToCurrHash.find(OldHash);
338 if (J == OldHashToCurrHash.end())
339 OldHashToCurrHash.insert({OldHash, CurrHash});
340 else if (J->second != CurrHash)
341 return false;
342 }
343
344 return true;
345}
346
347// Validate the locations pointed by a param has the same hash and Constant.
348static bool
350 const IndexInstrMap &IndexInstruction,
351 const ParamLocsVecTy &ParamLocsVec) {
352 for (auto &ParamLocs : ParamLocsVec) {
353 std::optional<stable_hash> OldHash;
354 std::optional<Constant *> OldConst;
355 for (auto &Loc : ParamLocs) {
356 assert(SF.IndexOperandHashMap->count(Loc));
357 auto CurrHash = SF.IndexOperandHashMap->at(Loc);
358 auto [InstIndex, OpndIndex] = Loc;
359 assert(InstIndex < IndexInstruction.size());
360 const auto *Inst = IndexInstruction.lookup(InstIndex);
361 auto *CurrConst = cast<Constant>(Inst->getOperand(OpndIndex));
362 if (!OldHash) {
363 OldHash = CurrHash;
364 OldConst = CurrConst;
365 } else if (CurrConst != *OldConst || CurrHash != *OldHash) {
366 return false;
367 }
368 }
369 }
370 return true;
371}
372
373static ParamLocsVecTy
375 std::map<std::vector<stable_hash>, ParamLocs> HashSeqToLocs;
376 auto &RSF = *SFS[0];
377 unsigned StableFunctionCount = SFS.size();
378
379 for (auto &[IndexPair, Hash] : *RSF.IndexOperandHashMap) {
380 // Const hash sequence across stable functions.
381 // We will allocate a parameter per unique hash squence.
382 // can't use SmallVector as key
383 std::vector<stable_hash> ConstHashSeq;
384 ConstHashSeq.push_back(Hash);
385 bool Identical = true;
386 for (unsigned J = 1; J < StableFunctionCount; ++J) {
387 auto &SF = SFS[J];
388 auto SHash = SF->IndexOperandHashMap->at(IndexPair);
389 if (Hash != SHash)
390 Identical = false;
391 ConstHashSeq.push_back(SHash);
392 }
393
394 if (Identical)
395 continue;
396
397 // For each unique Const hash sequence (parameter), add the locations.
398 HashSeqToLocs[ConstHashSeq].push_back(IndexPair);
399 }
400
401 ParamLocsVecTy ParamLocsVec;
402 for (auto &[HashSeq, Locs] : HashSeqToLocs)
403 ParamLocsVec.push_back(std::move(Locs));
404
405 llvm::sort(ParamLocsVec, [&](const ParamLocs &L, const ParamLocs &R) {
406 return L[0] < R[0];
407 });
408
409 return ParamLocsVec;
410}
411
412bool GlobalMergeFunc::merge(Module &M, const StableFunctionMap *FunctionMap) {
413 bool Changed = false;
414
415 // Collect stable functions related to the current module.
417 HashToFuncs;
418 for (auto &F : M) {
419 if (!isEligibleFunction(&F))
420 continue;
421 auto FI = hashFunction(F);
422 if (FunctionMap->contains(FI.FunctionHash))
423 HashToFuncs[FI.FunctionHash].emplace_back(&F, std::move(FI));
424 }
425
426 for (auto &[Hash, Funcs] : HashToFuncs) {
427 std::optional<ParamLocsVecTy> ParamLocsVec;
428 SmallVector<FuncMergeInfo> FuncMergeInfos;
429 auto &SFS = FunctionMap->at(Hash);
430 assert(!SFS.empty());
431 auto &RFS = SFS[0];
432
433 // Iterate functions with the same hash.
434 for (auto &[F, FI] : Funcs) {
435 // Check if the function is compatible with any stable function
436 // in terms of the number of instructions and ignored operands.
437 if (RFS->InstCount != FI.IndexInstruction->size())
438 continue;
439
440 auto hasValidSharedConst = [&](StableFunctionMap::StableFunctionEntry *SF,
441 FunctionHashInfo &FHI) {
442 for (auto &[Index, Hash] : *SF->IndexOperandHashMap) {
443 auto [InstIndex, OpndIndex] = Index;
444 assert(InstIndex < FHI.IndexInstruction->size());
445 auto *Inst = FHI.IndexInstruction->lookup(InstIndex);
446 if (!ignoreOp(Inst, OpndIndex))
447 return false;
448 }
449 return true;
450 };
451 if (!hasValidSharedConst(RFS.get(), FI))
452 continue;
453
454 for (auto &SF : SFS) {
455 assert(SF->InstCount == FI.IndexInstruction->size());
456 assert(hasValidSharedConst(SF.get(), FI));
457 // Check if there is any stable function that is compatiable with the
458 // current one.
460 *FI.IndexOperandHashMap))
461 continue;
462 if (!ParamLocsVec.has_value()) {
463 ParamLocsVec = computeParamInfo(SFS);
464 LLVM_DEBUG(dbgs() << "[GlobalMergeFunc] Merging hash: " << Hash
465 << " with Params " << ParamLocsVec->size() << "\n");
466 }
467 if (!checkConstLocationCompatible(*SF, *FI.IndexInstruction,
468 *ParamLocsVec))
469 continue;
470
471 // If a stable function matching the current one is found,
472 // create a candidate for merging and proceed to the next function.
473 FuncMergeInfos.emplace_back(SF.get(), F, FI.IndexInstruction.get());
474 break;
475 }
476 }
477 unsigned FuncMergeInfoSize = FuncMergeInfos.size();
478 if (FuncMergeInfoSize == 0)
479 continue;
480
481 LLVM_DEBUG(dbgs() << "[GlobalMergeFunc] Merging function count "
482 << FuncMergeInfoSize << " for hash: " << Hash << "\n");
483
484 for (auto &FMI : FuncMergeInfos) {
485 Changed = true;
486
487 // We've already validated all locations of constant operands pointed by
488 // the parameters. Populate parameters pointing to the original constants.
490 SmallVector<Type *> ParamTypes;
491 for (auto &ParamLocs : *ParamLocsVec) {
492 assert(!ParamLocs.empty());
493 auto &[InstIndex, OpndIndex] = ParamLocs[0];
494 auto *Inst = FMI.IndexInstruction->lookup(InstIndex);
495 auto *Opnd = cast<Constant>(Inst->getOperand(OpndIndex));
496 Params.push_back(Opnd);
497 ParamTypes.push_back(Opnd->getType());
498 }
499
500 // Create a merged function derived from the current function.
501 Function *MergedFunc =
502 createMergedFunction(FMI, ParamTypes, *ParamLocsVec);
503
504 LLVM_DEBUG({
505 dbgs() << "[GlobalMergeFunc] Merged function (hash:" << FMI.SF->Hash
506 << ") " << MergedFunc->getName() << " generated from "
507 << FMI.F->getName() << ":\n";
508 MergedFunc->dump();
509 });
510
511 // Transform the current function into a thunk that calls the merged
512 // function.
513 createThunk(FMI, Params, MergedFunc);
514 LLVM_DEBUG({
515 dbgs() << "[GlobalMergeFunc] Thunk generated: \n";
516 FMI.F->dump();
517 });
518 ++NumMergedFunctions;
519 }
520 }
521
522 return Changed;
523}
524
526 // Initialize the local function map regardless of the merger mode.
527 LocalFunctionMap = std::make_unique<StableFunctionMap>();
528
529 // Disable codegen data for merging. The local merge is still enabled.
531 return;
532
533 // (Full)LTO module does not have functions added to the index.
534 // In this case, we run a local merger without using codegen data.
535 if (Index && !Index->hasExportedFunctions(M))
536 return;
537
538 if (cgdata::emitCGData())
542}
543
545 LLVM_DEBUG(dbgs() << "Emit function map. Size: " << LocalFunctionMap->size()
546 << "\n");
547 // No need to emit the function map if it is empty.
548 if (LocalFunctionMap->empty())
549 return;
551 raw_svector_ostream OS(Buf);
552
553 std::vector<CGDataPatchItem> PatchItems;
554 StableFunctionMapRecord::serialize(OS, LocalFunctionMap.get(), PatchItems);
555 CGDataOStream COS(OS);
556 COS.patch(PatchItems);
557
558 std::unique_ptr<MemoryBuffer> Buffer = MemoryBuffer::getMemBuffer(
559 OS.str(), "in-memory stable function map", false);
560
561 Triple TT(M.getTargetTriple());
562 embedBufferInModule(M, *Buffer,
563 getCodeGenDataSectionName(CG_merge, TT.getObjectFormat()),
564 Align(4));
565}
566
569
570 const StableFunctionMap *FuncMap;
571 if (MergerMode == HashFunctionMode::UsingHashFunction) {
572 // Use the prior CG data to optimistically create global merge candidates.
574 } else {
575 analyze(M);
576 // Emit the local function map to the custom section, __llvm_merge before
577 // finalizing it.
580 LocalFunctionMap->finalize();
581 FuncMap = LocalFunctionMap.get();
582 }
583
584 return merge(M, FuncMap);
585}
586
587namespace {
588
589class GlobalMergeFuncPassWrapper : public ModulePass {
590
591public:
592 static char ID;
593
594 GlobalMergeFuncPassWrapper() : ModulePass(ID) {}
595
596 void getAnalysisUsage(AnalysisUsage &AU) const override {
598 AU.setPreservesAll();
600 }
601
602 StringRef getPassName() const override { return "Global Merge Functions"; }
603
604 bool runOnModule(Module &M) override;
605};
606
607} // namespace
608
609char GlobalMergeFuncPassWrapper::ID = 0;
610INITIALIZE_PASS(GlobalMergeFuncPassWrapper, "global-merge-func",
611 "Global merge function pass", false, false)
612
614 return new GlobalMergeFuncPassWrapper();
615}
616
617bool GlobalMergeFuncPassWrapper::runOnModule(Module &M) {
618 const ModuleSummaryIndex *Index = nullptr;
619 if (auto *IndexWrapperPass =
620 getAnalysisIfAvailable<ImmutableModuleSummaryIndexWrapperPass>())
621 Index = IndexWrapperPass->getIndex();
622
623 return GlobalMergeFunc(Index).run(M);
624}
625
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static FunctionHashInfo hashFunction(const Function &F)
static bool checkConstHashCompatible(const DenseMap< IndexPair, stable_hash > &OldInstOpndIndexToConstHash, const DenseMap< IndexPair, stable_hash > &CurrInstOpndIndexToConstHash)
static ParamLocsVecTy computeParamInfo(const StableFunctionMap::StableFunctionEntries &SFS)
static cl::opt< bool > DisableCGDataForMerging("disable-cgdata-for-merging", cl::Hidden, cl::desc("Disable codegen data for function merging. Local " "merging is still enabled within a module."), cl::init(false))
static bool canParameterizeCallOperand(const CallBase *CI, unsigned OpIdx)
static Function * createMergedFunction(FuncMergeInfo &FI, ArrayRef< Type * > ConstParamTypes, const ParamLocsVecTy &ParamLocsVec)
static void createThunk(FuncMergeInfo &FI, ArrayRef< Constant * > Params, Function *ToFunc)
static bool isEligibleInstructionForConstantSharing(const Instruction *I)
static bool ignoreOp(const Instruction *I, unsigned OpIdx)
bool isEligibleFunction(Function *F)
Returns true if function F is eligible for merging.
static bool checkConstLocationCompatible(const StableFunctionMap::StableFunctionEntry &SF, const IndexInstrMap &IndexInstruction, const ParamLocsVecTy &ParamLocsVec)
static bool isCalleeOperand(const CallBase *CI, unsigned OpIdx)
Returns true if the \OpIdx operand of CI is the callee operand.
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
Machine Check Debug Module
This is the interface to build a ModuleSummaryIndex for a module.
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
Definition PassSupport.h:56
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
Definition Statistic.h:171
#define LLVM_DEBUG(...)
Definition Debug.h:119
A container for analyses that lazily runs them and caches their results.
Represent the analysis usage information of a pass.
AnalysisUsage & addUsedIfAvailable()
Add the specified Pass class to the set of analyses used by this pass.
void setPreservesAll()
Set by analyses that do not transform their input at all.
This class represents an incoming formal argument to a Function.
Definition Argument.h:32
Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
iterator end() const
Definition ArrayRef.h:130
size_t size() const
Get the array size.
Definition ArrayRef.h:141
iterator begin() const
Definition ArrayRef.h:129
LLVM Basic Block Representation.
Definition BasicBlock.h:62
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
Definition BasicBlock.h:206
A wrapper class to abstract writer stream with support of bytes back patching.
LLVM_ABI void patch(ArrayRef< CGDataPatchItem > P)
Base class for all callable instructions (InvokeInst and CallInst) Holds everything related to callin...
bool isInlineAsm() const
Check if this call is an inline asm statement.
void setCallingConv(CallingConv::ID CC)
bool isOperandBundleOfType(uint32_t ID, unsigned Idx) const
Return true if the operand at index Idx is a bundle operand that has tag ID ID.
std::optional< OperandBundleUse > getOperandBundle(StringRef Name) const
Return an operand bundle by name, if present.
Value * getCalledOperand() const
const Use & getCalledOperandUse() const
void setAttributes(AttributeList A)
Set the attributes for this call.
This class represents a function call, abstracting a target machine's calling convention.
void setTailCallKind(TailCallKind TCK)
iterator find(const_arg_type_t< KeyT > Val)
Definition DenseMap.h:767
iterator end()
Definition DenseMap.h:687
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition DenseMap.h:828
unsigned getNumParams() const
Return the number of fixed parameters this function type requires.
static LLVM_ABI FunctionType * get(Type *Result, ArrayRef< Type * > Params, bool isVarArg)
This static method is the primary way of constructing a FunctionType.
void addFnAttr(Attribute::AttrKind Kind)
Add function attributes to this function.
Definition Function.cpp:644
void setSubprogram(DISubprogram *SP)
Set the attached subprogram.
static Function * Create(FunctionType *Ty, LinkageTypes Linkage, unsigned AddrSpace, const Twine &N="", Module *M=nullptr)
Definition Function.h:169
void splice(Function::iterator ToIt, Function *FromF)
Transfer all blocks from FromF to this function at ToIt.
Definition Function.h:746
FunctionType * getFunctionType() const
Returns the FunctionType for me.
Definition Function.h:212
CallingConv::ID getCallingConv() const
getCallingConv()/setCallingConv(CC) - These method get and set the calling convention of this functio...
Definition Function.h:273
AttributeList getAttributes() const
Return the attribute list for this Function.
Definition Function.h:329
iterator begin()
Definition Function.h:838
arg_iterator arg_begin()
Definition Function.h:853
void setEntryCount(uint64_t Count, const DenseSet< GlobalValue::GUID > *Imports=nullptr)
Set the entry count for this function.
Argument * getArg(unsigned i) const
Definition Function.h:871
void copyAttributesFrom(const Function *Src)
copyAttributesFrom - copy all additional attributes (those not needed to create a Function) from the ...
Definition Function.cpp:849
GlobalMergeFunc is a ModulePass that implements a function merging mechanism using stable function ha...
LLVM_ABI void analyze(Module &M)
Analyze module to create stable function into LocalFunctionMap.
LLVM_ABI void initializeMergerMode(const Module &M)
LLVM_ABI bool merge(Module &M, const StableFunctionMap *FunctionMap)
Merge functions in the module using the given function map.
LLVM_ABI void emitFunctionMap(Module &M)
Emit LocalFunctionMap into __llvm_merge section.
LLVM_ABI bool run(Module &M)
static constexpr char MergingInstanceSuffix[]
The suffix used to identify the merged function that parameterizes the constant values.
void setDLLStorageClass(DLLStorageClassTypes C)
void setLinkage(LinkageTypes LT)
@ InternalLinkage
Rename collisions when linking (static functions).
Definition GlobalValue.h:60
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
Definition IRBuilder.h:2918
Legacy wrapper pass to provide the ModuleSummaryIndex object.
ValueT lookup(const KeyT &Key) const
Definition MapVector.h:110
size_type size() const
Definition MapVector.h:58
static std::unique_ptr< MemoryBuffer > getMemBuffer(StringRef InputData, StringRef BufferName="", bool RequiresNullTerminator=true)
Open the specified memory range as a MemoryBuffer.
ModulePass class - This class is used to implement unstructured interprocedural optimizations and ana...
Definition Pass.h:255
Class to hold module path string table and global value map, and encapsulate methods for operating on...
A Module instance is used to store all the information related to an LLVM module.
Definition Module.h:68
virtual void getAnalysisUsage(AnalysisUsage &) const
getAnalysisUsage - This function should be overriden by passes that need analysis information to do t...
Definition Pass.cpp:113
A set of analyses that are preserved following a run of a transformation pass.
Definition Analysis.h:112
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
Definition Analysis.h:115
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
Definition Analysis.h:118
reference emplace_back(ArgTypes &&... Args)
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.
std::string str() const
Get the contents as an std::string.
Definition StringRef.h:222
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:48
const Use & getOperandUse(unsigned i) const
Definition User.h:220
Value * getOperand(unsigned i) const
Definition User.h:207
Type * getType() const
All values are typed, get the type of this value.
Definition Value.h:257
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
Definition Value.cpp:553
LLVM_ABI const Value * stripPointerCasts() const
Strip off pointer casts, all-zero GEPs and address space casts.
Definition Value.cpp:712
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
Definition Value.cpp:319
LLVM_ABI void dump() const
Support for debugging, callable in GDB: V->dump()
A raw_ostream that writes to an SmallVector or SmallString.
StringRef str() const
Return a StringRef for the vector contents.
Changed
@ SwiftTail
This follows the Swift calling convention in how arguments are passed but guarantees tail calls will ...
Definition CallingConv.h:87
bool hasStableFunctionMap()
bool emitCGData()
const StableFunctionMap * getStableFunctionMap()
initializer< Ty > init(const Ty &Val)
This is an optimization pass for GlobalISel generic memory operations.
auto size(R &&Range, std::enable_if_t< std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< decltype(Range.begin())>::iterator_category >::value, void > *=nullptr)
Get the size of a range.
Definition STLExtras.h:1685
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
MapVector< unsigned, Instruction * > IndexInstrMap
A map from an instruction index to an instruction pointer.
LLVM_ABI ModulePass * createGlobalMergeFuncPass()
This pass performs merging similar functions globally.
SmallVector< IndexPairHash > IndexOperandHashVecType
auto dyn_cast_or_null(const Y &Val)
Definition Casting.h:753
void sort(IteratorTy Start, IteratorTy End)
Definition STLExtras.h:1652
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:209
StringRef get_stable_name(StringRef Name)
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...
Definition Casting.h:547
SmallVector< IndexPair, 4 > ParamLocs
std::pair< unsigned, unsigned > IndexPair
The pair of an instruction index and a operand index.
LLVM_ABI FunctionHashInfo StructuralHashWithDifferences(const Function &F, IgnoreOperandFunc IgnoreOp, bool SourceQualifyLocalGlobals=false)
Computes a structural hash of a given function, considering the structure and content of the function...
SmallVector< ParamLocs, 8 > ParamLocsVecTy
OutputIt move(R &&Range, OutputIt Out)
Provide wrappers to std::move which take ranges instead of having to pass begin/end explicitly.
Definition STLExtras.h:1933
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
LLVM_ABI GlobalVariable * embedBufferInModule(Module &M, MemoryBufferRef Buf, StringRef SectionName, Align Alignment=Align(1), bool SectionExclude=true)
Embed the memory buffer Buf into the module M as a global using the specified section name.
LLVM_ABI std::string getCodeGenDataSectionName(CGDataSectKind CGSK, Triple::ObjectFormatType OF, bool AddSegmentInfo=true)
Implement std::hash so that hash_code can be used in STL containers.
Definition BitVector.h:878
Tuple to hold function info to process merging.
FuncMergeInfo(StableFunctionMap::StableFunctionEntry *SF, Function *F, IndexInstrMap *IndexInstruction)
StableFunctionMap::StableFunctionEntry * SF
IndexInstrMap * IndexInstruction
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition Alignment.h:39
LLVM_ABI PreservedAnalyses run(Module &M, AnalysisManager< Module > &)
const ModuleSummaryIndex * ImportSummary
static LLVM_ABI void serialize(raw_ostream &OS, const StableFunctionMap *FunctionMap, std::vector< CGDataPatchItem > &PatchItems)
A static helper function to serialize the stable function map without owning the stable function map.
An efficient form of StableFunction for fast look-up.
std::unique_ptr< IndexOperandHashMapType > IndexOperandHashMap
A map from an IndexPair to a stable_hash which was skipped.
unsigned InstCount
The number of instructions.
SmallVector< std::unique_ptr< StableFunctionEntry > > StableFunctionEntries
LLVM_ABI const StableFunctionEntries & at(HashFuncsMapType::key_type FunctionHash) const
bool contains(HashFuncsMapType::key_type FunctionHash) const
A stable function is a function with a stable hash while tracking the locations of ignored operands a...