LLVM 24.0.0git
MachineOutliner.cpp
Go to the documentation of this file.
1//===---- MachineOutliner.cpp - Outline instructions -----------*- 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/// \file
10/// Replaces repeated sequences of instructions with function calls.
11///
12/// This works by placing every instruction from every basic block in a
13/// suffix tree, and repeatedly querying that tree for repeated sequences of
14/// instructions. If a sequence of instructions appears often, then it ought
15/// to be beneficial to pull out into a function.
16///
17/// The MachineOutliner communicates with a given target using hooks defined in
18/// TargetInstrInfo.h. The target supplies the outliner with information on how
19/// a specific sequence of instructions should be outlined. This information
20/// is used to deduce the number of instructions necessary to
21///
22/// * Create an outlined function
23/// * Call that outlined function
24///
25/// Targets must implement
26/// * getOutliningCandidateInfo
27/// * buildOutlinedFrame
28/// * insertOutlinedCall
29/// * isFunctionSafeToOutlineFrom
30///
31/// in order to make use of the MachineOutliner.
32///
33/// This was originally presented at the 2016 LLVM Developers' Meeting in the
34/// talk "Reducing Code Size Using Outlining". For a high-level overview of
35/// how this pass works, the talk is available on YouTube at
36///
37/// https://www.youtube.com/watch?v=yorld-WSOeU
38///
39/// The slides for the talk are available at
40///
41/// http://www.llvm.org/devmtg/2016-11/Slides/Paquette-Outliner.pdf
42///
43/// The talk provides an overview of how the outliner finds candidates and
44/// ultimately outlines them. It describes how the main data structure for this
45/// pass, the suffix tree, is queried and purged for candidates. It also gives
46/// a simplified suffix tree construction algorithm for suffix trees based off
47/// of the algorithm actually used here, Ukkonen's algorithm.
48///
49/// For the original RFC for this pass, please see
50///
51/// http://lists.llvm.org/pipermail/llvm-dev/2016-August/104170.html
52///
53/// For more information on the suffix tree data structure, please see
54/// https://www.cs.helsinki.fi/u/ukkonen/SuffixT1withFigs.pdf
55///
56//===----------------------------------------------------------------------===//
58#include "llvm/ADT/DenseMap.h"
59#include "llvm/ADT/SmallSet.h"
60#include "llvm/ADT/Statistic.h"
61#include "llvm/ADT/Twine.h"
71#include "llvm/CodeGen/Passes.h"
75#include "llvm/IR/DIBuilder.h"
76#include "llvm/IR/IRBuilder.h"
77#include "llvm/IR/Mangler.h"
78#include "llvm/IR/Module.h"
81#include "llvm/Support/Debug.h"
86#include <tuple>
87#include <vector>
88
89#define DEBUG_TYPE "machine-outliner"
90
91using namespace llvm;
92using namespace ore;
93using namespace outliner;
94
95// Statistics for outlined functions.
96STATISTIC(NumOutlined, "Number of candidates outlined");
97STATISTIC(FunctionsCreated, "Number of functions created");
98
99// Statistics for instruction mapping.
100STATISTIC(NumLegalInUnsignedVec, "Outlinable instructions mapped");
101STATISTIC(NumIllegalInUnsignedVec,
102 "Unoutlinable instructions mapped + number of sentinel values");
103STATISTIC(NumSentinels, "Sentinel values inserted during mapping");
104STATISTIC(NumInvisible,
105 "Non-debug invisible instructions skipped during mapping");
106STATISTIC(UnsignedVecSize,
107 "Total number of instructions mapped and saved to mapping vector");
108STATISTIC(StableHashAttempts,
109 "Count of hashing attempts made for outlined functions");
110STATISTIC(StableHashDropped,
111 "Count of unsuccessful hashing attempts for outlined functions");
112STATISTIC(NumRemovedLOHs, "Total number of Linker Optimization Hints removed");
113STATISTIC(NumPGOBlockedOutlined,
114 "Number of times outlining was blocked by PGO");
115STATISTIC(NumPGOAllowedCold,
116 "Number of times outlining was allowed from cold functions");
117STATISTIC(NumPGOConservativeBlockedOutlined,
118 "Number of times outlining was blocked conservatively when profile "
119 "counts were missing");
120STATISTIC(NumPGOOptimisticOutlined,
121 "Number of times outlining was allowed optimistically when profile "
122 "counts were missing");
123
124// Set to true if the user wants the outliner to run on linkonceodr linkage
125// functions. This is false by default because the linker can dedupe linkonceodr
126// functions. Since the outliner is confined to a single module (modulo LTO),
127// this is off by default. It should, however, be the default behaviour in
128// LTO.
130 "enable-linkonceodr-outlining", cl::Hidden,
131 cl::desc("Enable the machine outliner on linkonceodr functions"),
132 cl::init(false));
133
134/// Number of times to re-run the outliner. This is not the total number of runs
135/// as the outliner will run at least one time. The default value is set to 0,
136/// meaning the outliner will run one time and rerun zero times after that.
138 "machine-outliner-reruns", cl::init(0), cl::Hidden,
139 cl::desc(
140 "Number of times to rerun the outliner after the initial outline"));
141
143 "outliner-benefit-threshold", cl::init(1), cl::Hidden,
144 cl::desc(
145 "The minimum size in bytes before an outlining candidate is accepted"));
146
148 "outliner-leaf-descendants", cl::init(true), cl::Hidden,
149 cl::desc("Consider all leaf descendants of internal nodes of the suffix "
150 "tree as candidates for outlining (if false, only leaf children "
151 "are considered)"));
152
153static cl::opt<bool>
154 DisableGlobalOutlining("disable-global-outlining", cl::Hidden,
155 cl::desc("Disable global outlining only by ignoring "
156 "the codegen data generation or use"),
157 cl::init(false));
158
160 "append-content-hash-outlined-name", cl::Hidden,
161 cl::desc("This appends the content hash to the globally outlined function "
162 "name. It's beneficial for enhancing the precision of the stable "
163 "hash and for ordering the outlined functions."),
164 cl::init(true));
165
166namespace {
167
168/// Maps \p MachineInstrs to unsigned integers and stores the mappings.
169struct InstructionMapper {
170 const MachineModuleInfo &MMI;
171
172 /// The next available integer to assign to a \p MachineInstr that
173 /// cannot be outlined.
174 ///
175 /// Set to -3 for compatability with \p DenseMapInfo<unsigned>.
176 unsigned IllegalInstrNumber = -3;
177
178 /// The next available integer to assign to a \p MachineInstr that can
179 /// be outlined.
180 unsigned LegalInstrNumber = 0;
181
182 /// Correspondence from \p MachineInstrs to unsigned integers.
184 InstructionIntegerMap;
185
186 /// Correspondence between \p MachineBasicBlocks and target-defined flags.
188
189 /// The vector of unsigned integers that the module is mapped to.
190 SmallVector<unsigned> UnsignedVec;
191
192 /// Stores the location of the instruction associated with the integer
193 /// at index i in \p UnsignedVec for each index i.
195
196 // Set if we added an illegal number in the previous step.
197 // Since each illegal number is unique, we only need one of them between
198 // each range of legal numbers. This lets us make sure we don't add more
199 // than one illegal number per range.
200 bool AddedIllegalLastTime = false;
201
202 /// Maps \p *It to a legal integer.
203 ///
204 /// Updates \p CanOutlineWithPrevInstr, \p HaveLegalRange, \p InstrListForMBB,
205 /// \p UnsignedVecForMBB, \p InstructionIntegerMap, and \p LegalInstrNumber.
206 ///
207 /// \returns The integer that \p *It was mapped to.
208 unsigned mapToLegalUnsigned(
209 MachineBasicBlock::iterator &It, bool &CanOutlineWithPrevInstr,
210 bool &HaveLegalRange, unsigned &NumLegalInBlock,
211 SmallVector<unsigned> &UnsignedVecForMBB,
213 // We added something legal, so we should unset the AddedLegalLastTime
214 // flag.
215 AddedIllegalLastTime = false;
216
217 // If we have at least two adjacent legal instructions (which may have
218 // invisible instructions in between), remember that.
219 if (CanOutlineWithPrevInstr)
220 HaveLegalRange = true;
221 CanOutlineWithPrevInstr = true;
222
223 // Keep track of the number of legal instructions we insert.
224 NumLegalInBlock++;
225
226 // Get the integer for this instruction or give it the current
227 // LegalInstrNumber.
228 InstrListForMBB.push_back(It);
229 MachineInstr &MI = *It;
230 bool WasInserted;
232 ResultIt;
233 std::tie(ResultIt, WasInserted) =
234 InstructionIntegerMap.insert(std::make_pair(&MI, LegalInstrNumber));
235 unsigned MINumber = ResultIt->second;
236
237 // There was an insertion.
238 if (WasInserted)
239 LegalInstrNumber++;
240
241 UnsignedVecForMBB.push_back(MINumber);
242
243 // Make sure we don't overflow or use any integers reserved by the DenseMap.
244 if (LegalInstrNumber >= IllegalInstrNumber)
245 report_fatal_error("Instruction mapping overflow!");
246
247 // Statistics.
248 ++NumLegalInUnsignedVec;
249 return MINumber;
250 }
251
252 /// Maps \p *It to an illegal integer.
253 ///
254 /// Updates \p InstrListForMBB, \p UnsignedVecForMBB, and \p
255 /// IllegalInstrNumber.
256 ///
257 /// \returns The integer that \p *It was mapped to.
258 unsigned mapToIllegalUnsigned(
259 MachineBasicBlock::iterator &It, bool &CanOutlineWithPrevInstr,
260 SmallVector<unsigned> &UnsignedVecForMBB,
262 // Can't outline an illegal instruction. Set the flag.
263 CanOutlineWithPrevInstr = false;
264
265 // Only add one illegal number per range of legal numbers.
266 if (AddedIllegalLastTime)
267 return IllegalInstrNumber;
268
269 // Remember that we added an illegal number last time.
270 AddedIllegalLastTime = true;
271 unsigned MINumber = IllegalInstrNumber;
272
273 InstrListForMBB.push_back(It);
274 UnsignedVecForMBB.push_back(IllegalInstrNumber);
275 IllegalInstrNumber--;
276 // Statistics.
277 ++NumIllegalInUnsignedVec;
278
279 assert(LegalInstrNumber < IllegalInstrNumber &&
280 "Instruction mapping overflow!");
281
282 return MINumber;
283 }
284
285 /// Transforms a \p MachineBasicBlock into a \p vector of \p unsigneds
286 /// and appends it to \p UnsignedVec and \p InstrList.
287 ///
288 /// Two instructions are assigned the same integer if they are identical.
289 /// If an instruction is deemed unsafe to outline, then it will be assigned an
290 /// unique integer. The resulting mapping is placed into a suffix tree and
291 /// queried for candidates.
292 ///
293 /// \param MBB The \p MachineBasicBlock to be translated into integers.
294 /// \param TII \p TargetInstrInfo for the function.
295 void convertToUnsignedVec(MachineBasicBlock &MBB,
296 const TargetInstrInfo &TII) {
297 LLVM_DEBUG(dbgs() << "*** Converting MBB '" << MBB.getName()
298 << "' to unsigned vector ***\n");
299 unsigned Flags = 0;
300
301 // Don't even map in this case.
302 if (!TII.isMBBSafeToOutlineFrom(MBB, Flags))
303 return;
304
305 auto OutlinableRanges = TII.getOutlinableRanges(MBB, Flags);
306 LLVM_DEBUG(dbgs() << MBB.getName() << ": " << OutlinableRanges.size()
307 << " outlinable range(s)\n");
308 if (OutlinableRanges.empty())
309 return;
310
311 // Store info for the MBB for later outlining.
312 MBBFlagsMap[&MBB] = Flags;
313
315
316 // The number of instructions in this block that will be considered for
317 // outlining.
318 unsigned NumLegalInBlock = 0;
319
320 // True if we have at least two legal instructions which aren't separated
321 // by an illegal instruction.
322 bool HaveLegalRange = false;
323
324 // True if we can perform outlining given the last mapped (non-invisible)
325 // instruction. This lets us know if we have a legal range.
326 bool CanOutlineWithPrevInstr = false;
327
328 // FIXME: Should this all just be handled in the target, rather than using
329 // repeated calls to getOutliningType?
330 SmallVector<unsigned> UnsignedVecForMBB;
332
333 LLVM_DEBUG(dbgs() << "*** Mapping outlinable ranges ***\n");
334 for (auto &OutlinableRange : OutlinableRanges) {
335 auto OutlinableRangeBegin = OutlinableRange.first;
336 auto OutlinableRangeEnd = OutlinableRange.second;
337#ifndef NDEBUG
339 dbgs() << "Mapping "
340 << std::distance(OutlinableRangeBegin, OutlinableRangeEnd)
341 << " instruction range\n");
342 // Everything outside of an outlinable range is illegal.
343 unsigned NumSkippedInRange = 0;
344#endif
345 for (; It != OutlinableRangeBegin; ++It) {
346 if (It->isDebugInstr())
347 continue;
348#ifndef NDEBUG
349 ++NumSkippedInRange;
350#endif
351 mapToIllegalUnsigned(It, CanOutlineWithPrevInstr, UnsignedVecForMBB,
352 InstrListForMBB);
353 }
354#ifndef NDEBUG
355 LLVM_DEBUG(dbgs() << "Skipped " << NumSkippedInRange
356 << " instructions outside outlinable range\n");
357#endif
358 assert(It != MBB.end() && "Should still have instructions?");
359 // `It` is now positioned at the beginning of a range of instructions
360 // which may be outlinable. Check if each instruction is known to be safe.
361 for (; It != OutlinableRangeEnd; ++It) {
362 if (It->isDebugInstr())
363 continue;
364 // Keep track of where this instruction is in the module.
365 switch (TII.getOutliningType(MMI, It, Flags)) {
366 case InstrType::Illegal:
367 mapToIllegalUnsigned(It, CanOutlineWithPrevInstr, UnsignedVecForMBB,
368 InstrListForMBB);
369 break;
370
371 case InstrType::Legal:
372 mapToLegalUnsigned(It, CanOutlineWithPrevInstr, HaveLegalRange,
373 NumLegalInBlock, UnsignedVecForMBB,
374 InstrListForMBB);
375 break;
376
377 case InstrType::LegalTerminator:
378 mapToLegalUnsigned(It, CanOutlineWithPrevInstr, HaveLegalRange,
379 NumLegalInBlock, UnsignedVecForMBB,
380 InstrListForMBB);
381 // The instruction also acts as a terminator, so we have to record
382 // that in the string.
383 mapToIllegalUnsigned(It, CanOutlineWithPrevInstr, UnsignedVecForMBB,
384 InstrListForMBB);
385 break;
386
387 case InstrType::Invisible:
388 // Normally this is set by mapTo(Blah)Unsigned, but we just want to
389 // skip this instruction. So, unset the flag here.
390 ++NumInvisible;
391 AddedIllegalLastTime = false;
392 break;
393 }
394 }
395 }
396
397 LLVM_DEBUG(dbgs() << "HaveLegalRange = " << HaveLegalRange << "\n");
398
399 // Are there enough legal instructions in the block for outlining to be
400 // possible?
401 if (HaveLegalRange) {
402 // After we're done every insertion, uniquely terminate this part of the
403 // "string". This makes sure we won't match across basic block or function
404 // boundaries since the "end" is encoded uniquely and thus appears in no
405 // repeated substring.
406 mapToIllegalUnsigned(It, CanOutlineWithPrevInstr, UnsignedVecForMBB,
407 InstrListForMBB);
408 ++NumSentinels;
409 append_range(InstrList, InstrListForMBB);
410 append_range(UnsignedVec, UnsignedVecForMBB);
411 }
412 }
413
414 InstructionMapper(const MachineModuleInfo &MMI_) : MMI(MMI_) {}
415};
416
417/// An interprocedural pass which finds repeated sequences of
418/// instructions and replaces them with calls to functions.
419///
420/// Each instruction is mapped to an unsigned integer and placed in a string.
421/// The resulting mapping is then placed in a \p SuffixTree. The \p SuffixTree
422/// is then repeatedly queried for repeated sequences of instructions. Each
423/// non-overlapping repeated sequence is then placed in its own
424/// \p MachineFunction and each instance is then replaced with a call to that
425/// function.
426struct MachineOutliner : public ModulePass {
427
428 static char ID;
429
430 MachineModuleInfo *MMI = nullptr;
431 const TargetMachine *TM = nullptr;
432
433 /// Set to true if the outliner should consider functions with
434 /// linkonceodr linkage.
435 bool OutlineFromLinkOnceODRs = false;
436
437 /// The current repeat number of machine outlining.
438 unsigned OutlineRepeatedNum = 0;
439
440 /// The mode for whether to run the outliner
441 /// Set to always-outline by default for compatibility with llc's -run-pass
442 /// option.
443 RunOutliner RunOutlinerMode = RunOutliner::AlwaysOutline;
444
445 /// This is a compact representation of hash sequences of outlined functions.
446 /// It is used when OutlinerMode = CGDataMode::Write.
447 /// The resulting hash tree will be emitted into __llvm_outlined section
448 /// which will be dead-stripped not going to the final binary.
449 /// A post-process using llvm-cgdata, lld, or ThinLTO can merge them into
450 /// a global oulined hash tree for the subsequent codegen.
451 std::unique_ptr<OutlinedHashTree> LocalHashTree;
452
453 /// The mode of the outliner.
454 /// When is's CGDataMode::None, candidates are populated with the suffix tree
455 /// within a module and outlined.
456 /// When it's CGDataMode::Write, in addition to CGDataMode::None, the hash
457 /// sequences of outlined functions are published into LocalHashTree.
458 /// When it's CGDataMode::Read, candidates are populated with the global
459 /// outlined hash tree that has been built by the previous codegen.
460 CGDataMode OutlinerMode = CGDataMode::None;
461
462 StringRef getPassName() const override { return "Machine Outliner"; }
463
464 void getAnalysisUsage(AnalysisUsage &AU) const override {
465 AU.addRequired<MachineModuleInfoWrapperPass>();
466 AU.addRequired<TargetPassConfig>();
467 AU.addPreserved<MachineModuleInfoWrapperPass>();
468 AU.addUsedIfAvailable<ImmutableModuleSummaryIndexWrapperPass>();
469 if (RunOutlinerMode == RunOutliner::OptimisticPGO ||
470 RunOutlinerMode == RunOutliner::ConservativePGO) {
471 AU.addRequired<BlockFrequencyInfoWrapperPass>();
472 AU.addRequired<ProfileSummaryInfoWrapperPass>();
473 }
474 AU.setPreservesAll();
475 ModulePass::getAnalysisUsage(AU);
476 }
477
478 MachineOutliner() : ModulePass(ID) {}
479
480 /// Remark output explaining that not outlining a set of candidates would be
481 /// better than outlining that set.
482 void emitNotOutliningCheaperRemark(
483 unsigned StringLen, std::vector<Candidate> &CandidatesForRepeatedSeq,
484 OutlinedFunction &OF);
485
486 /// Run the outlining cost model for a group of candidates and append the
487 /// resulting outlined function if it is profitable.
488 void createOutlinedFunctionIfBeneficial(
489 std::vector<Candidate> &Candidates, unsigned StringLen,
490 unsigned MinRepeats, const TargetInstrInfo &TII,
491 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList);
492
493 /// Remark output explaining that a function was outlined.
494 void emitOutlinedFunctionRemark(OutlinedFunction &OF);
495
496 /// Find all repeated substrings that satisfy the outlining cost model by
497 /// constructing a suffix tree.
498 ///
499 /// If a substring appears at least twice, then it must be represented by
500 /// an internal node which appears in at least two suffixes. Each suffix
501 /// is represented by a leaf node. To do this, we visit each internal node
502 /// in the tree, using the leaf children of each internal node. If an
503 /// internal node represents a beneficial substring, then we use each of
504 /// its leaf children to find the locations of its substring.
505 ///
506 /// \param Mapper Contains outlining mapping information.
507 /// \param[out] FunctionList Filled with a list of \p OutlinedFunctions
508 /// each type of candidate.
509 void
510 findCandidates(InstructionMapper &Mapper,
511 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList);
512
513 /// Find all repeated substrings that match in the global outlined hash
514 /// tree built from the previous codegen.
515 ///
516 /// \param Mapper Contains outlining mapping information.
517 /// \param[out] FunctionList Filled with a list of \p OutlinedFunctions
518 /// each type of candidate.
519 void findGlobalCandidates(
520 InstructionMapper &Mapper,
521 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList);
522
523 /// Replace the sequences of instructions represented by \p OutlinedFunctions
524 /// with calls to functions.
525 ///
526 /// \param M The module we are outlining from.
527 /// \param FunctionList A list of functions to be inserted into the module.
528 /// \param Mapper Contains the instruction mappings for the module.
529 /// \param[out] OutlinedFunctionNum The outlined function number.
530 bool outline(Module &M,
531 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList,
532 InstructionMapper &Mapper, unsigned &OutlinedFunctionNum);
533
534 /// Creates a function for \p OF and inserts it into the module.
535 MachineFunction *createOutlinedFunction(Module &M, OutlinedFunction &OF,
536 InstructionMapper &Mapper,
537 unsigned Name);
538
539 /// Compute and publish the stable hash sequence of instructions in the
540 /// outlined function, \p MF. The parameter \p CandSize represents the number
541 /// of candidates that have identical instruction sequences to \p MF.
542 void computeAndPublishHashSequence(MachineFunction &MF, unsigned CandSize);
543
544 /// Initialize the outliner mode.
545 void initializeOutlinerMode(const Module &M);
546
547 /// Emit the outlined hash tree into __llvm_outline section.
548 void emitOutlinedHashTree(Module &M);
549
550 /// Calls 'doOutline()' 1 + OutlinerReruns times.
551 bool runOnModule(Module &M) override;
552
553 /// Construct a suffix tree on the instructions in \p M and outline repeated
554 /// strings from that tree.
555 bool doOutline(Module &M, unsigned &OutlinedFunctionNum);
556
557 /// Return a DISubprogram for OF if one exists, and null otherwise. Helper
558 /// function for remark emission.
559 DISubprogram *getSubprogramOrNull(const OutlinedFunction &OF) {
560 for (const Candidate &C : OF.Candidates)
561 if (MachineFunction *MF = C.getMF())
562 if (DISubprogram *SP = MF->getFunction().getSubprogram())
563 return SP;
564 return nullptr;
565 }
566
567 /// Populate and \p InstructionMapper with instruction-to-integer mappings.
568 /// These are used to construct a suffix tree.
569 void populateMapper(InstructionMapper &Mapper, Module &M);
570
571 /// Initialize information necessary to output a size remark.
572 /// FIXME: This should be handled by the pass manager, not the outliner.
573 /// FIXME: This is nearly identical to the initSizeRemarkInfo in the legacy
574 /// pass manager.
575 void initSizeRemarkInfo(const Module &M,
576 StringMap<unsigned> &FunctionToInstrCount);
577
578 /// Emit the remark.
579 // FIXME: This should be handled by the pass manager, not the outliner.
580 void
581 emitInstrCountChangedRemark(const Module &M,
582 const StringMap<unsigned> &FunctionToInstrCount);
583};
584} // Anonymous namespace.
585
586char MachineOutliner::ID = 0;
587
589 MachineOutliner *OL = new MachineOutliner();
590 OL->RunOutlinerMode = RunOutlinerMode;
591 return OL;
592}
593
594INITIALIZE_PASS(MachineOutliner, DEBUG_TYPE, "Machine Function Outliner", false,
595 false)
596
597void MachineOutliner::emitNotOutliningCheaperRemark(
598 unsigned StringLen, std::vector<Candidate> &CandidatesForRepeatedSeq,
599 OutlinedFunction &OF) {
600 // FIXME: Right now, we arbitrarily choose some Candidate from the
601 // OutlinedFunction. This isn't necessarily fixed, nor does it have to be.
602 // We should probably sort these by function name or something to make sure
603 // the remarks are stable.
604 Candidate &C = CandidatesForRepeatedSeq.front();
605 MachineOptimizationRemarkEmitter MORE(*(C.getMF()), nullptr);
606 MORE.emit([&]() {
607 MachineOptimizationRemarkMissed R(DEBUG_TYPE, "NotOutliningCheaper",
608 C.front().getDebugLoc(), C.getMBB());
609 R << "Did not outline " << NV("Length", StringLen) << " instructions"
610 << " from " << NV("NumOccurrences", CandidatesForRepeatedSeq.size())
611 << " locations."
612 << " Bytes from outlining all occurrences ("
613 << NV("OutliningCost", OF.getOutliningCost()) << ")"
614 << " >= Unoutlined instruction bytes ("
615 << NV("NotOutliningCost", OF.getNotOutlinedCost()) << ")"
616 << " (Also found at: ";
617
618 // Tell the user the other places the candidate was found.
619 for (unsigned i = 1, e = CandidatesForRepeatedSeq.size(); i < e; i++) {
620 R << NV((Twine("OtherStartLoc") + Twine(i)).str(),
621 CandidatesForRepeatedSeq[i].front().getDebugLoc());
622 if (i != e - 1)
623 R << ", ";
624 }
625
626 R << ")";
627 return R;
628 });
629}
630
631void MachineOutliner::emitOutlinedFunctionRemark(OutlinedFunction &OF) {
632 MachineBasicBlock *MBB = &*OF.MF->begin();
633 MachineOptimizationRemarkEmitter MORE(*OF.MF, nullptr);
634 MachineOptimizationRemark R(DEBUG_TYPE, "OutlinedFunction",
636 R << "Saved " << NV("OutliningBenefit", OF.getBenefit()) << " bytes by "
637 << "outlining " << NV("Length", OF.getNumInstrs()) << " instructions "
638 << "from " << NV("NumOccurrences", OF.getOccurrenceCount())
639 << " locations. "
640 << "(Found at: ";
641
642 // Tell the user the other places the candidate was found.
643 for (size_t i = 0, e = OF.Candidates.size(); i < e; i++) {
644
645 R << NV((Twine("StartLoc") + Twine(i)).str(),
646 OF.Candidates[i].front().getDebugLoc());
647 if (i != e - 1)
648 R << ", ";
649 }
650
651 R << ")";
652
653 MORE.emit(R);
654}
655
657 // Globals with local linkage are qualified with their module's source file
658 // name so that same-named locals in different modules do not match when hash
659 // sequences are compared across modules.
660 return stableHashValue(MI, /*HashVRegs=*/false,
661 /*HashConstantPoolIndices=*/false,
662 /*HashMemOperands=*/false,
663 /*SourceQualifyLocalGlobals=*/true);
664}
665
667 unsigned StartIdx;
668 unsigned EndIdx;
669 unsigned Count;
670 MatchedEntry(unsigned StartIdx, unsigned EndIdx, unsigned Count)
672 MatchedEntry() = delete;
673};
674
675// Find all matches in the global outlined hash tree.
676// It's quadratic complexity in theory, but it's nearly linear in practice
677// since the length of outlined sequences are small within a block.
678static SmallVector<MatchedEntry> getMatchedEntries(InstructionMapper &Mapper) {
679 auto &InstrList = Mapper.InstrList;
680 auto &UnsignedVec = Mapper.UnsignedVec;
681
682 SmallVector<MatchedEntry> MatchedEntries;
683 auto Size = UnsignedVec.size();
684
685 // Get the global outlined hash tree built from the previous run.
686 const cl::LibraryOptionsContext &LibraryOptions =
687 Mapper.MMI.getModule()->getContext().getLibraryOptions();
688 assert(cgdata::hasOutlinedHashTree(LibraryOptions));
689 const auto *RootNode = cgdata::getOutlinedHashTree(LibraryOptions)->getRoot();
690
691 auto getValidInstr = [&](unsigned Index) -> const MachineInstr * {
692 if (UnsignedVec[Index] >= Mapper.LegalInstrNumber)
693 return nullptr;
694 return &(*InstrList[Index]);
695 };
696
697 auto getStableHashAndFollow =
698 [](const MachineInstr &MI, const HashNode *CurrNode) -> const HashNode * {
699 stable_hash StableHash = hashInstruction(MI);
700 if (!StableHash)
701 return nullptr;
702 auto It = CurrNode->Successors.find(StableHash);
703 return (It == CurrNode->Successors.end()) ? nullptr : It->second.get();
704 };
705
706 for (unsigned I = 0; I < Size; ++I) {
707 const MachineInstr *MI = getValidInstr(I);
708 if (!MI || MI->isDebugInstr())
709 continue;
710 const HashNode *CurrNode = getStableHashAndFollow(*MI, RootNode);
711 if (!CurrNode)
712 continue;
713
714 for (unsigned J = I + 1; J < Size; ++J) {
715 const MachineInstr *MJ = getValidInstr(J);
716 if (!MJ)
717 break;
718 // Skip debug instructions as we did for the outlined function.
719 if (MJ->isDebugInstr())
720 continue;
721 CurrNode = getStableHashAndFollow(*MJ, CurrNode);
722 if (!CurrNode)
723 break;
724 // Even with a match ending with a terminal, we continue finding
725 // matches to populate all candidates.
726 if (auto Count = CurrNode->Terminals)
727 MatchedEntries.emplace_back(I, J, *Count);
728 }
729 }
730
731 return MatchedEntries;
732}
733
734void MachineOutliner::findGlobalCandidates(
735 InstructionMapper &Mapper,
736 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList) {
737 FunctionList.clear();
738 auto &InstrList = Mapper.InstrList;
739 auto &MBBFlagsMap = Mapper.MBBFlagsMap;
740
741 std::vector<Candidate> CandidatesForRepeatedSeq;
742 for (auto &ME : getMatchedEntries(Mapper)) {
743 CandidatesForRepeatedSeq.clear();
744 MachineBasicBlock::iterator StartIt = InstrList[ME.StartIdx];
745 MachineBasicBlock::iterator EndIt = InstrList[ME.EndIdx];
746 auto Length = ME.EndIdx - ME.StartIdx + 1;
747 MachineBasicBlock *MBB = StartIt->getParent();
748 CandidatesForRepeatedSeq.emplace_back(ME.StartIdx, Length, StartIt, EndIt,
749 MBB, MBBFlagsMap[MBB]);
750 const TargetInstrInfo *TII =
752 unsigned MinRepeats = 1;
753 std::optional<std::unique_ptr<OutlinedFunction>> OF =
754 TII->getOutliningCandidateInfo(*MMI, CandidatesForRepeatedSeq,
755 MinRepeats);
756 if (!OF.has_value() || OF.value()->Candidates.empty())
757 continue;
758 // We create a global candidate for each match.
759 assert(OF.value()->Candidates.size() == MinRepeats);
760 FunctionList.emplace_back(std::make_unique<GlobalOutlinedFunction>(
761 std::move(OF.value()), ME.Count));
762 }
763}
764
766 const Function &F = C.getMF()->getFunction();
767 return F.hasSection() ? F.getSection() : StringRef();
768}
769
771partitionCandidatesByInputSection(std::vector<Candidate> &Candidates) {
772 // Each candidate belongs to exactly one MachineFunction, so the partitions
773 // are disjoint and can be outlined independently.
775 SmallVector<StringRef> Sections;
776 for (Candidate &C : Candidates) {
778 auto It = llvm::find(Sections, Section);
779 if (It == Sections.end()) {
780 Sections.push_back(Section);
781 Partitions.emplace_back();
782 It = Sections.end() - 1;
783 }
784 Partitions[std::distance(Sections.begin(), It)].push_back(std::move(C));
785 }
786 return Partitions;
787}
788
789void MachineOutliner::createOutlinedFunctionIfBeneficial(
790 std::vector<Candidate> &Candidates, unsigned StringLen, unsigned MinRepeats,
791 const TargetInstrInfo &TII,
792 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList) {
793 if (Candidates.size() < MinRepeats)
794 return;
795
796 std::optional<std::unique_ptr<OutlinedFunction>> OF =
797 TII.getOutliningCandidateInfo(*MMI, Candidates, MinRepeats);
798
799 // If we deleted too many candidates, then there's nothing worth outlining.
800 // FIXME: This should take target-specified instruction sizes into account.
801 if (!OF.has_value() || OF.value()->Candidates.size() < MinRepeats)
802 return;
803
804 // Is it better to outline this candidate than not?
805 if (OF.value()->getBenefit() < OutlinerBenefitThreshold) {
806 emitNotOutliningCheaperRemark(StringLen, Candidates, *OF.value());
807 return;
808 }
809
810 FunctionList.emplace_back(std::move(OF.value()));
811}
812
813void MachineOutliner::findCandidates(
814 InstructionMapper &Mapper,
815 std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList) {
816 FunctionList.clear();
817 SuffixTree ST(Mapper.UnsignedVec, OutlinerLeafDescendants);
818
819 // First, find all of the repeated substrings in the tree of minimum length
820 // 2.
821 std::vector<Candidate> CandidatesForRepeatedSeq;
822 LLVM_DEBUG(dbgs() << "*** Discarding overlapping candidates *** \n");
824 dbgs() << "Searching for overlaps in all repeated sequences...\n");
825 for (SuffixTree::RepeatedSubstring &RS : ST) {
826 CandidatesForRepeatedSeq.clear();
827 unsigned StringLen = RS.Length;
828 LLVM_DEBUG(dbgs() << " Sequence length: " << StringLen << "\n");
829 // Debug code to keep track of how many candidates we removed.
830#ifndef NDEBUG
831 unsigned NumDiscarded = 0;
832 unsigned NumKept = 0;
833#endif
834 // Sort the start indices so that we can efficiently check if candidates
835 // overlap with the ones we've already found for this sequence.
836 llvm::sort(RS.StartIndices);
837 for (const unsigned &StartIdx : RS.StartIndices) {
838 // Trick: Discard some candidates that would be incompatible with the
839 // ones we've already found for this sequence. This will save us some
840 // work in candidate selection.
841 //
842 // If two candidates overlap, then we can't outline them both. This
843 // happens when we have candidates that look like, say
844 //
845 // AA (where each "A" is an instruction).
846 //
847 // We might have some portion of the module that looks like this:
848 // AAAAAA (6 A's)
849 //
850 // In this case, there are 5 different copies of "AA" in this range, but
851 // at most 3 can be outlined. If only outlining 3 of these is going to
852 // be unbeneficial, then we ought to not bother.
853 //
854 // Note that two things DON'T overlap when they look like this:
855 // start1...end1 .... start2...end2
856 // That is, one must either
857 // * End before the other starts
858 // * Start after the other ends
859 unsigned EndIdx = StartIdx + StringLen - 1;
860 if (!CandidatesForRepeatedSeq.empty() &&
861 StartIdx <= CandidatesForRepeatedSeq.back().getEndIdx()) {
862#ifndef NDEBUG
863 ++NumDiscarded;
864 LLVM_DEBUG(dbgs() << " .. DISCARD candidate @ [" << StartIdx << ", "
865 << EndIdx << "]; overlaps with candidate @ ["
866 << CandidatesForRepeatedSeq.back().getStartIdx()
867 << ", " << CandidatesForRepeatedSeq.back().getEndIdx()
868 << "]\n");
869#endif
870 continue;
871 }
872 // It doesn't overlap with anything, so we can outline it.
873 // Each sequence is over [StartIt, EndIt].
874 // Save the candidate and its location.
875#ifndef NDEBUG
876 ++NumKept;
877#endif
878 MachineBasicBlock::iterator StartIt = Mapper.InstrList[StartIdx];
879 MachineBasicBlock::iterator EndIt = Mapper.InstrList[EndIdx];
880 MachineBasicBlock *MBB = StartIt->getParent();
881 CandidatesForRepeatedSeq.emplace_back(StartIdx, StringLen, StartIt, EndIt,
882 MBB, Mapper.MBBFlagsMap[MBB]);
883 }
884#ifndef NDEBUG
885 LLVM_DEBUG(dbgs() << " Candidates discarded: " << NumDiscarded
886 << "\n");
887 LLVM_DEBUG(dbgs() << " Candidates kept: " << NumKept << "\n\n");
888#endif
889 unsigned MinRepeats = 2;
890
891 // We've found something we might want to outline.
892 // Create an OutlinedFunction to store it and check if it'd be beneficial
893 // to outline.
894 if (CandidatesForRepeatedSeq.size() < MinRepeats)
895 continue;
896
897 // Arbitrarily choose a TII from the first candidate.
898 // FIXME: Should getOutliningCandidateInfo move to TargetMachine?
899 const TargetInstrInfo *TII =
900 CandidatesForRepeatedSeq[0].getMF()->getSubtarget().getInstrInfo();
901
902 // Targets that do not opt in to section aware outlining never map
903 // functions with a section marking, so every candidate would land in a
904 // single partition. Skip partitioning entirely to avoid the allocation.
905 if (!TII->supportsSectionAwareOutlining()) {
906 createOutlinedFunctionIfBeneficial(CandidatesForRepeatedSeq, StringLen,
907 MinRepeats, *TII, FunctionList);
908 continue;
909 }
910
912 dbgs()
913 << "*** Section Aware Outlining is enabled for the target *** \n");
914
916 partitionCandidatesByInputSection(CandidatesForRepeatedSeq);
917 LLVM_DEBUG(dbgs() << " Input section partitions: " << Partitions.size()
918 << "\n");
919
920 for (std::vector<Candidate> &Partition : Partitions) {
921 LLVM_DEBUG({
922 StringRef Section = getCandidateInputSection(Partition.front());
923 dbgs() << " .. section '"
924 << (Section.empty() ? StringRef("<none>") : Section)
925 << "': " << Partition.size() << " candidates\n";
926 });
927 createOutlinedFunctionIfBeneficial(Partition, StringLen, MinRepeats, *TII,
928 FunctionList);
929 }
930 }
931}
932
933void MachineOutliner::computeAndPublishHashSequence(MachineFunction &MF,
934 unsigned CandSize) {
935 // Compute the hash sequence for the outlined function.
936 SmallVector<stable_hash> OutlinedHashSequence;
937 for (auto &MBB : MF) {
938 for (auto &NewMI : MBB) {
939 stable_hash Hash = hashInstruction(NewMI);
940 if (!Hash) {
941 OutlinedHashSequence.clear();
942 break;
943 }
944 OutlinedHashSequence.push_back(Hash);
945 }
946 }
947
948 // Append a unique name based on the non-empty hash sequence.
949 if (AppendContentHashToOutlinedName && !OutlinedHashSequence.empty()) {
950 auto CombinedHash = stable_hash_combine(OutlinedHashSequence);
951 auto NewName =
952 MF.getName().str() + ".content." + std::to_string(CombinedHash);
953 MF.getFunction().setName(NewName);
954 }
955
956 // Publish the non-empty hash sequence to the local hash tree.
957 if (OutlinerMode == CGDataMode::Write) {
958 StableHashAttempts++;
959 if (!OutlinedHashSequence.empty())
960 LocalHashTree->insert({OutlinedHashSequence, CandSize});
961 else
962 StableHashDropped++;
963 }
964}
965
966MachineFunction *MachineOutliner::createOutlinedFunction(
967 Module &M, OutlinedFunction &OF, InstructionMapper &Mapper, unsigned Name) {
968
969 // Create the function name. This should be unique.
970 // FIXME: We should have a better naming scheme. This should be stable,
971 // regardless of changes to the outliner's cost model/traversal order.
972 std::string FunctionName = "OUTLINED_FUNCTION_";
973 if (OutlineRepeatedNum > 0)
974 FunctionName += std::to_string(OutlineRepeatedNum + 1) + "_";
975 FunctionName += std::to_string(Name);
976 LLVM_DEBUG(dbgs() << "NEW FUNCTION: " << FunctionName << "\n");
977
978 // Create the function using an IR-level function.
979 LLVMContext &C = M.getContext();
980 Function *F = Function::Create(FunctionType::get(Type::getVoidTy(C), false),
981 Function::ExternalLinkage, FunctionName, M);
982
983 // NOTE: If this is linkonceodr, then we can take advantage of linker deduping
984 // which gives us better results when we outline from linkonceodr functions.
985 F->setLinkage(GlobalValue::InternalLinkage);
986 F->setUnnamedAddr(GlobalValue::UnnamedAddr::Global);
987
988 // Set optsize/minsize, so we don't insert padding between outlined
989 // functions.
990 F->addFnAttr(Attribute::OptimizeForSize);
991 F->addFnAttr(Attribute::MinSize);
992
993 Candidate &FirstCand = OF.Candidates.front();
994 const TargetInstrInfo &TII =
995 *FirstCand.getMF()->getSubtarget().getInstrInfo();
996
997 TII.mergeOutliningCandidateAttributes(*F, OF.Candidates);
998
999 if (TII.supportsSectionAwareOutlining()) {
1000 const Function &ParentFn = FirstCand.getMF()->getFunction();
1001 if (ParentFn.hasSection()) {
1002 F->setSection(ParentFn.getSection());
1003 LLVM_DEBUG(dbgs() << " INHERITED SECTION: " << ParentFn.getSection()
1004 << "\n");
1005 }
1006 }
1007
1008 // Set uwtable, so we generate eh_frame.
1009 UWTableKind UW = std::accumulate(
1010 OF.Candidates.cbegin(), OF.Candidates.cend(), UWTableKind::None,
1011 [](UWTableKind K, const outliner::Candidate &C) {
1012 return std::max(K, C.getMF()->getFunction().getUWTableKind());
1013 });
1014 F->setUWTableKind(UW);
1015
1016 BasicBlock *EntryBB = BasicBlock::Create(C, "entry", F);
1017 IRBuilder<> Builder(EntryBB);
1018 Builder.CreateRetVoid();
1019
1020 MachineModuleInfo &MMI = getAnalysis<MachineModuleInfoWrapperPass>().getMMI();
1022 MF.setIsOutlined(true);
1023 MachineBasicBlock &MBB = *MF.CreateMachineBasicBlock();
1024
1025 // Insert the new function into the module.
1026 MF.insert(MF.begin(), &MBB);
1027
1028 MachineFunction *OriginalMF = FirstCand.front().getMF();
1029 const std::vector<MCCFIInstruction> &Instrs =
1030 OriginalMF->getFrameInstructions();
1031 for (auto &MI : FirstCand) {
1032 if (MI.isDebugInstr())
1033 continue;
1034
1035 // Don't keep debug information for outlined instructions.
1036 auto DL = DebugLoc();
1037 if (MI.isCFIInstruction()) {
1038 unsigned CFIIndex = MI.getOperand(0).getCFIIndex();
1039 MCCFIInstruction CFI = Instrs[CFIIndex];
1040 BuildMI(MBB, MBB.end(), DL, TII.get(TargetOpcode::CFI_INSTRUCTION))
1041 .addCFIIndex(MF.addFrameInst(CFI));
1042 } else {
1043 MachineInstr &NewMI = TII.duplicate(MBB, MBB.end(), MI);
1044 NewMI.dropMemRefs(MF);
1045 NewMI.setDebugLoc(DL);
1046 NewMI.clearKillInfo();
1047 // Also clear debug locations and kill info on any bundled instructions.
1048 if (NewMI.isBundledWithSucc()) {
1049 auto BundleEnd = getBundleEnd(NewMI.getIterator());
1050 for (auto I = std::next(NewMI.getIterator()); I != BundleEnd; ++I) {
1051 I->setDebugLoc(DL);
1052 I->clearKillInfo();
1053 }
1054 }
1055 }
1056 }
1057
1058 if (OutlinerMode != CGDataMode::None)
1059 computeAndPublishHashSequence(MF, OF.Candidates.size());
1060
1061 // Set normal properties for a late MachineFunction.
1062 MF.getProperties().resetIsSSA();
1063 MF.getProperties().setNoPHIs();
1064 MF.getProperties().setNoVRegs();
1065 MF.getProperties().setTracksLiveness();
1067
1068 // Compute live-in set for outlined fn
1069 const MachineRegisterInfo &MRI = MF.getRegInfo();
1070 const TargetRegisterInfo &TRI = *MRI.getTargetRegisterInfo();
1071 LivePhysRegs LiveIns(TRI);
1072 for (auto &Cand : OF.Candidates) {
1073 // Figure out live-ins at the first instruction.
1074 MachineBasicBlock &OutlineBB = *Cand.front().getParent();
1075 LivePhysRegs CandLiveIns(TRI);
1076 CandLiveIns.addLiveOuts(OutlineBB);
1077 for (const MachineInstr &MI :
1078 reverse(make_range(Cand.begin(), OutlineBB.end())))
1079 CandLiveIns.stepBackward(MI);
1080
1081 // The live-in set for the outlined function is the union of the live-ins
1082 // from all the outlining points.
1083 for (MCPhysReg Reg : CandLiveIns)
1084 LiveIns.addReg(Reg);
1085 }
1086 addLiveIns(MBB, LiveIns);
1087
1088 TII.buildOutlinedFrame(MBB, MF, OF);
1089
1090 // If there's a DISubprogram associated with this outlined function, then
1091 // emit debug info for the outlined function.
1092 if (DISubprogram *SP = getSubprogramOrNull(OF)) {
1093 // We have a DISubprogram. Get its DICompileUnit.
1094 DICompileUnit *CU = SP->getUnit();
1095 DIBuilder DB(M, true, CU);
1096 DIFile *Unit = SP->getFile();
1097 Mangler Mg;
1098 // Get the mangled name of the function for the linkage name.
1099 std::string Dummy;
1100 raw_string_ostream MangledNameStream(Dummy);
1101 Mg.getNameWithPrefix(MangledNameStream, F, false);
1102
1103 DISubprogram *OutlinedSP = DB.createFunction(
1104 Unit /* Context */, F->getName(), StringRef(Dummy), Unit /* File */,
1105 0 /* Line 0 is reserved for compiler-generated code. */,
1106 DB.createSubroutineType(DB.getOrCreateTypeArray({})), /* void type */
1107 0, /* Line 0 is reserved for compiler-generated code. */
1108 DINode::DIFlags::FlagArtificial /* Compiler-generated code. */,
1109 /* Outlined code is optimized code by definition. */
1110 DISubprogram::SPFlagDefinition | DISubprogram::SPFlagOptimized);
1111
1112 // Attach subprogram to the function.
1113 F->setSubprogram(OutlinedSP);
1114 // We're done with the DIBuilder.
1115 DB.finalize();
1116 }
1117
1118 return &MF;
1119}
1120
1121bool MachineOutliner::outline(
1122 Module &M, std::vector<std::unique_ptr<OutlinedFunction>> &FunctionList,
1123 InstructionMapper &Mapper, unsigned &OutlinedFunctionNum) {
1124 LLVM_DEBUG(dbgs() << "*** Outlining ***\n");
1125 LLVM_DEBUG(dbgs() << "NUMBER OF POTENTIAL FUNCTIONS: " << FunctionList.size()
1126 << "\n");
1127 bool OutlinedSomething = false;
1128
1129 // Sort by priority where priority := getNotOutlinedCost / getOutliningCost.
1130 // The function with highest priority should be outlined first.
1131 stable_sort(FunctionList, [](const std::unique_ptr<OutlinedFunction> &LHS,
1132 const std::unique_ptr<OutlinedFunction> &RHS) {
1133 return LHS->getNotOutlinedCost() * RHS->getOutliningCost() >
1134 RHS->getNotOutlinedCost() * LHS->getOutliningCost();
1135 });
1136
1137 // Walk over each function, outlining them as we go along. Functions are
1138 // outlined greedily, based off the sort above.
1139 auto *UnsignedVecBegin = Mapper.UnsignedVec.begin();
1140 LLVM_DEBUG(dbgs() << "WALKING FUNCTION LIST\n");
1141 for (auto &OF : FunctionList) {
1142#ifndef NDEBUG
1143 auto NumCandidatesBefore = OF->Candidates.size();
1144#endif
1145 // If we outlined something that overlapped with a candidate in a previous
1146 // step, then we can't outline from it.
1147 erase_if(OF->Candidates, [&UnsignedVecBegin](Candidate &C) {
1148 return std::any_of(UnsignedVecBegin + C.getStartIdx(),
1149 UnsignedVecBegin + C.getEndIdx() + 1, [](unsigned I) {
1150 return I == static_cast<unsigned>(-1);
1151 });
1152 });
1153
1154#ifndef NDEBUG
1155 auto NumCandidatesAfter = OF->Candidates.size();
1156 LLVM_DEBUG(dbgs() << "PRUNED: " << NumCandidatesBefore - NumCandidatesAfter
1157 << "/" << NumCandidatesBefore << " candidates\n");
1158#endif
1159
1160 // If we made it unbeneficial to outline this function, skip it.
1161 if (OF->getBenefit() < OutlinerBenefitThreshold) {
1162 LLVM_DEBUG(dbgs() << "SKIP: Expected benefit (" << OF->getBenefit()
1163 << " B) < threshold (" << OutlinerBenefitThreshold
1164 << " B)\n");
1165 continue;
1166 }
1167
1168 LLVM_DEBUG(dbgs() << "OUTLINE: Expected benefit (" << OF->getBenefit()
1169 << " B) > threshold (" << OutlinerBenefitThreshold
1170 << " B)\n");
1171
1172 // Remove all Linker Optimization Hints from the candidates.
1173 // TODO: The intersection of the LOHs from all candidates should be legal in
1174 // the outlined function.
1175 SmallPtrSet<MachineInstr *, 2> MIs;
1176 for (Candidate &C : OF->Candidates) {
1177 for (MachineInstr &MI : C)
1178 MIs.insert(&MI);
1179 NumRemovedLOHs += TM->clearLinkerOptimizationHints(MIs);
1180 MIs.clear();
1181 }
1182
1183 // It's beneficial. Create the function and outline its sequence's
1184 // occurrences.
1185 OF->MF = createOutlinedFunction(M, *OF, Mapper, OutlinedFunctionNum);
1186 emitOutlinedFunctionRemark(*OF);
1187 FunctionsCreated++;
1188 OutlinedFunctionNum++; // Created a function, move to the next name.
1189 MachineFunction *MF = OF->MF;
1190 const TargetSubtargetInfo &STI = MF->getSubtarget();
1191 const TargetInstrInfo &TII = *STI.getInstrInfo();
1192
1193 // Replace occurrences of the sequence with calls to the new function.
1194 LLVM_DEBUG(dbgs() << "CREATE OUTLINED CALLS\n");
1195 for (Candidate &C : OF->Candidates) {
1196 MachineBasicBlock &MBB = *C.getMBB();
1197 MachineBasicBlock::iterator StartIt = C.begin();
1198 MachineBasicBlock::iterator EndIt = std::prev(C.end());
1199
1200 // Find the first non-debug instruction with a non-zero source line, and
1201 // merge the locations of the calls in the candidate that have one.
1202 DebugLoc FirstLoc, MergedCallLoc;
1203 for (MachineInstr &MI : C) {
1204 if (MI.isDebugInstr())
1205 continue;
1206 const DebugLoc &DL = MI.getDebugLoc();
1207 if (!DL || !DL.getLine())
1208 continue;
1209 if (!FirstLoc)
1210 FirstLoc = DL;
1211 if (MI.isCall())
1212 MergedCallLoc = MergedCallLoc
1213 ? DebugLoc::getMergedLocation(MergedCallLoc, DL)
1214 : DL;
1215 }
1216
1217 // Remember the instruction the call sequence will be inserted after, so
1218 // we can find every instruction the target inserts below.
1220 StartIt == MBB.begin() ? MBB.end() : std::prev(StartIt);
1221
1222 // Insert the call.
1223 auto CallInst = TII.insertOutlinedCall(M, MBB, StartIt, *MF, C);
1224
1225 // Unwinding through a call in the candidate symbolizes the caller frame
1226 // at the outlined call, so it should carry that call's location. With
1227 // multiple calls, every one of them is symbolized there, so use their
1228 // merged location: it may be less precise when the calls differ, but it
1229 // never attributes a call to an inlined scope it was not in. Nothing
1230 // returns to a tail branch, so it keeps the first location.
1231 DebugLoc CallLoc =
1232 !CallInst->isTerminator() && MergedCallLoc ? MergedCallLoc : FirstLoc;
1233
1234 // insertOutlinedCall may emit link register save/restore instructions
1235 // around the call, and leaves StartIt on the last instruction it
1236 // inserted. Give the whole sequence the same location. Otherwise, when
1237 // that location has a source line, a locationless save or restore can
1238 // introduce a line 0 row, including at the return address immediately
1239 // after the call.
1241 PrevIt == MBB.end() ? MBB.begin() : std::next(PrevIt);
1242 for (MachineInstr &MI : make_range(SeqBegin, std::next(StartIt)))
1243 MI.setDebugLoc(CallLoc);
1244
1245#ifndef NDEBUG
1246 auto MBBBeingOutlinedFromName =
1247 MBB.getName().empty() ? "<unknown>" : MBB.getName().str();
1248 auto MFBeingOutlinedFromName = MBB.getParent()->getName().empty()
1249 ? "<unknown>"
1250 : MBB.getParent()->getName().str();
1251 LLVM_DEBUG(dbgs() << " CALL: " << MF->getName() << " in "
1252 << MFBeingOutlinedFromName << ":"
1253 << MBBBeingOutlinedFromName << "\n");
1254 LLVM_DEBUG(dbgs() << " .. " << *CallInst);
1255#endif
1256
1257 // If the caller tracks liveness, then we need to make sure that
1258 // anything we outline doesn't break liveness assumptions. The outlined
1259 // functions themselves currently don't track liveness, but we should
1260 // make sure that the ranges we yank things out of aren't wrong.
1261 if (MBB.getParent()->getProperties().hasTracksLiveness()) {
1262 // The following code is to add implicit def operands to the call
1263 // instruction. It also updates call site information for moved
1264 // code.
1265 SmallSet<Register, 2> UseRegs, DefRegs;
1266 // Copy over the defs in the outlined range.
1267 // First inst in outlined range <-- Anything that's defined in this
1268 // ... .. range has to be added as an
1269 // implicit Last inst in outlined range <-- def to the call
1270 // instruction. Also remove call site information for outlined block
1271 // of code. The exposed uses need to be copied in the outlined range.
1273 Iter = EndIt.getReverse(),
1274 Last = std::next(CallInst.getReverse());
1275 Iter != Last; Iter++) {
1276 MachineInstr *MI = &*Iter;
1277 if (MI->isDebugInstr())
1278 continue;
1279 SmallSet<Register, 2> InstrUseRegs;
1280 for (MachineOperand &MOP : MI->operands()) {
1281 // Skip over anything that isn't a register.
1282 if (!MOP.isReg())
1283 continue;
1284
1285 if (MOP.isDef()) {
1286 // Introduce DefRegs set to skip the redundant register.
1287 DefRegs.insert(MOP.getReg());
1288 if (UseRegs.count(MOP.getReg()) &&
1289 !InstrUseRegs.count(MOP.getReg()))
1290 // Since the regiester is modeled as defined,
1291 // it is not necessary to be put in use register set.
1292 UseRegs.erase(MOP.getReg());
1293 } else if (!MOP.isUndef()) {
1294 // Any register which is not undefined should
1295 // be put in the use register set.
1296 UseRegs.insert(MOP.getReg());
1297 InstrUseRegs.insert(MOP.getReg());
1298 }
1299 }
1300 if (MI->isCandidateForAdditionalCallInfo())
1301 MI->getMF()->eraseAdditionalCallInfo(MI);
1302 }
1303
1304 for (const Register &I : DefRegs)
1305 // If it's a def, add it to the call instruction.
1306 CallInst->addOperand(
1307 MachineOperand::CreateReg(I, true, /* isDef = true */
1308 true /* isImp = true */));
1309
1310 for (const Register &I : UseRegs)
1311 // If it's a exposed use, add it to the call instruction.
1312 CallInst->addOperand(
1313 MachineOperand::CreateReg(I, false, /* isDef = false */
1314 true /* isImp = true */));
1315 }
1316
1317 // Erase from the point after where the call was inserted up to, and
1318 // including, the final instruction in the sequence.
1319 // Erase needs one past the end, so we need std::next there too.
1320 MBB.erase(std::next(StartIt), std::next(EndIt));
1321
1322 // Keep track of what we removed by marking them all as -1.
1323 for (unsigned &I : make_range(UnsignedVecBegin + C.getStartIdx(),
1324 UnsignedVecBegin + C.getEndIdx() + 1))
1325 I = static_cast<unsigned>(-1);
1326 OutlinedSomething = true;
1327
1328 // Statistics.
1329 NumOutlined++;
1330 }
1331 }
1332
1333 LLVM_DEBUG(dbgs() << "OutlinedSomething = " << OutlinedSomething << "\n");
1334 return OutlinedSomething;
1335}
1336
1337static bool allowPGOOutlining(RunOutliner RunOutlinerMode,
1338 const ProfileSummaryInfo *PSI,
1339 const BlockFrequencyInfo *BFI,
1341 if (RunOutlinerMode != RunOutliner::OptimisticPGO &&
1342 RunOutlinerMode != RunOutliner::ConservativePGO)
1343 return true;
1344 auto *MF = MBB.getParent();
1345 if (MF->getFunction().hasFnAttribute(Attribute::Cold)) {
1346 ++NumPGOAllowedCold;
1347 return true;
1348 }
1349
1350 auto *BB = MBB.getBasicBlock();
1351 if (BB && PSI && BFI)
1352 if (auto Count = BFI->getBlockProfileCount(BB))
1353 return *Count <= PSI->getOrCompColdCountThreshold();
1354
1355 if (RunOutlinerMode == RunOutliner::OptimisticPGO) {
1356 auto *TII = MF->getSubtarget().getInstrInfo();
1357 if (TII->shouldOutlineFromFunctionByDefault(*MF)) {
1358 // Profile data is unavailable, but we optimistically allow outlining
1359 ++NumPGOOptimisticOutlined;
1360 return true;
1361 }
1362 return false;
1363 }
1364 assert(RunOutlinerMode == RunOutliner::ConservativePGO);
1365 // Profile data is unavailable, so we conservatively block outlining
1366 ++NumPGOConservativeBlockedOutlined;
1367 return false;
1368}
1369
1370void MachineOutliner::populateMapper(InstructionMapper &Mapper, Module &M) {
1371 // Build instruction mappings for each function in the module. Start by
1372 // iterating over each Function in M.
1373 LLVM_DEBUG(dbgs() << "*** Populating mapper ***\n");
1374 bool EnableProfileGuidedOutlining =
1375 RunOutlinerMode == RunOutliner::OptimisticPGO ||
1376 RunOutlinerMode == RunOutliner::ConservativePGO;
1377 ProfileSummaryInfo *PSI = nullptr;
1378 if (EnableProfileGuidedOutlining)
1379 PSI = &getAnalysis<ProfileSummaryInfoWrapperPass>().getPSI();
1380 for (Function &F : M) {
1381 LLVM_DEBUG(dbgs() << "MAPPING FUNCTION: " << F.getName() << "\n");
1382
1383 if (F.hasFnAttribute(Attribute::NoOutline)) {
1384 LLVM_DEBUG(dbgs() << "SKIP: Function has nooutline attribute\n");
1385 continue;
1386 }
1387
1388 // There's something in F. Check if it has a MachineFunction associated with
1389 // it.
1391
1392 // If it doesn't, then there's nothing to outline from. Move to the next
1393 // Function.
1394 if (!MF) {
1395 LLVM_DEBUG(dbgs() << "SKIP: Function does not have a MachineFunction\n");
1396 continue;
1397 }
1398
1399 // If the function returns twice, skip it.
1400 // The context saved by functions such as setjmp will be different if
1401 // they take place within an outlined function.
1402 // Ex: Saved stack pointer will be different.
1403 if (F.hasFnAttribute(Attribute::ReturnsTwice)) {
1404 LLVM_DEBUG(dbgs() << "SKIP: Function has returnstwice attribute\n");
1405 continue;
1406 }
1407
1408 // If the function calls a function that can return twice, skip it,
1409 // for the same reasons.
1410 if (MF->exposesReturnsTwice()) {
1411 LLVM_DEBUG(dbgs() << "SKIP: Function calls a function with "
1412 "returnstwice attribute\n");
1413 continue;
1414 }
1415
1416 const TargetInstrInfo *TII = MF->getSubtarget().getInstrInfo();
1417 BlockFrequencyInfo *BFI = nullptr;
1418 if (EnableProfileGuidedOutlining && F.hasProfileData())
1419 BFI = &getAnalysis<BlockFrequencyInfoWrapperPass>(F).getBFI();
1420 if (RunOutlinerMode == RunOutliner::TargetDefault &&
1421 !TII->shouldOutlineFromFunctionByDefault(*MF)) {
1422 LLVM_DEBUG(dbgs() << "SKIP: Target does not want to outline from "
1423 "function by default\n");
1424 continue;
1425 }
1426
1427 // We have a MachineFunction. Ask the target if it's suitable for outlining.
1428 // If it isn't, then move on to the next Function in the module.
1429 if (!TII->isFunctionSafeToOutlineFrom(*MF, OutlineFromLinkOnceODRs)) {
1430 LLVM_DEBUG(dbgs() << "SKIP: " << MF->getName()
1431 << ": unsafe to outline from\n");
1432 continue;
1433 }
1434
1435 // We have a function suitable for outlining. Iterate over every
1436 // MachineBasicBlock in MF and try to map its instructions to a list of
1437 // unsigned integers.
1438 const unsigned MinMBBSize = 2;
1439
1440 for (MachineBasicBlock &MBB : *MF) {
1441 LLVM_DEBUG(dbgs() << " MAPPING MBB: '" << MBB.getName() << "'\n");
1442 // If there isn't anything in MBB, then there's no point in outlining from
1443 // it.
1444 // If there are fewer than 2 non-debug instructions in the MBB, then it
1445 // can't ever contain something worth outlining. Count raw instructions,
1446 // including bundle interiors, to preserve MBB.size() behavior. Pseudo
1447 // probes also retain their historical treatment as ordinary
1448 // instructions.
1449 // FIXME: This should be based off of the maximum size in B of an outlined
1450 // call versus the size in B of the MBB.
1452 MBB.instr_end(),
1453 /* SkipPseudoOp */ false),
1454 MinMBBSize)) {
1455 LLVM_DEBUG(dbgs() << " SKIP: MBB size less than minimum size of "
1456 << MinMBBSize << "\n");
1457 continue;
1458 }
1459
1460 // Check if MBB could be the target of an indirect branch. If it is, then
1461 // we don't want to outline from it.
1462 if (MBB.hasAddressTaken()) {
1463 LLVM_DEBUG(dbgs() << " SKIP: MBB's address is taken\n");
1464 continue;
1465 }
1466
1467 if (!allowPGOOutlining(RunOutlinerMode, PSI, BFI, MBB)) {
1468 ++NumPGOBlockedOutlined;
1469 continue;
1470 }
1471
1472 // MBB is suitable for outlining. Map it to a list of unsigneds.
1473 Mapper.convertToUnsignedVec(MBB, *TII);
1474 }
1475 }
1476 // Statistics.
1477 UnsignedVecSize = Mapper.UnsignedVec.size();
1478}
1479
1480void MachineOutliner::initSizeRemarkInfo(
1481 const Module &M, StringMap<unsigned> &FunctionToInstrCount) {
1482 // Collect instruction counts for every function. We'll use this to emit
1483 // per-function size remarks later.
1484 for (const Function &F : M) {
1486
1487 // We only care about MI counts here. If there's no MachineFunction at this
1488 // point, then there won't be after the outliner runs, so let's move on.
1489 if (!MF)
1490 continue;
1491 FunctionToInstrCount[F.getName().str()] = MF->getInstructionCount();
1492 }
1493}
1494
1495void MachineOutliner::emitInstrCountChangedRemark(
1496 const Module &M, const StringMap<unsigned> &FunctionToInstrCount) {
1497 // Iterate over each function in the module and emit remarks.
1498 // Note that we won't miss anything by doing this, because the outliner never
1499 // deletes functions.
1500 for (const Function &F : M) {
1502
1503 // The outliner never deletes functions. If we don't have a MF here, then we
1504 // didn't have one prior to outlining either.
1505 if (!MF)
1506 continue;
1507
1508 std::string Fname = std::string(F.getName());
1509 unsigned FnCountAfter = MF->getInstructionCount();
1510 unsigned FnCountBefore = 0;
1511
1512 // Check if the function was recorded before.
1513 auto It = FunctionToInstrCount.find(Fname);
1514
1515 // Did we have a previously-recorded size? If yes, then set FnCountBefore
1516 // to that.
1517 if (It != FunctionToInstrCount.end())
1518 FnCountBefore = It->second;
1519
1520 // Compute the delta and emit a remark if there was a change.
1521 int64_t FnDelta = static_cast<int64_t>(FnCountAfter) -
1522 static_cast<int64_t>(FnCountBefore);
1523 if (FnDelta == 0)
1524 continue;
1525
1526 MachineOptimizationRemarkEmitter MORE(*MF, nullptr);
1527 MORE.emit([&]() {
1528 MachineOptimizationRemarkAnalysis R("size-info", "FunctionMISizeChange",
1529 DiagnosticLocation(), &MF->front());
1530 R << DiagnosticInfoOptimizationBase::Argument("Pass", "Machine Outliner")
1531 << ": Function: "
1532 << DiagnosticInfoOptimizationBase::Argument("Function", F.getName())
1533 << ": MI instruction count changed from "
1534 << DiagnosticInfoOptimizationBase::Argument("MIInstrsBefore",
1535 FnCountBefore)
1536 << " to "
1537 << DiagnosticInfoOptimizationBase::Argument("MIInstrsAfter",
1538 FnCountAfter)
1539 << "; Delta: "
1540 << DiagnosticInfoOptimizationBase::Argument("Delta", FnDelta);
1541 return R;
1542 });
1543 }
1544}
1545
1546void MachineOutliner::initializeOutlinerMode(const Module &M) {
1548 return;
1549
1550 if (auto *IndexWrapperPass =
1551 getAnalysisIfAvailable<ImmutableModuleSummaryIndexWrapperPass>()) {
1552 auto *TheIndex = IndexWrapperPass->getIndex();
1553 // (Full)LTO module does not have functions added to the index.
1554 // In this case, we run the outliner without using codegen data as usual.
1555 if (TheIndex && !TheIndex->hasExportedFunctions(M))
1556 return;
1557 }
1558
1559 // When codegen data write is enabled, we want to write the local outlined
1560 // hash tree to the custom section, `__llvm_outline`.
1561 // When the outlined hash tree is available from the previous codegen data,
1562 // we want to read it to optimistically create global outlining candidates.
1563 const cl::LibraryOptionsContext &LibraryOptions =
1564 M.getContext().getLibraryOptions();
1565 if (cgdata::emitCGData(LibraryOptions)) {
1566 OutlinerMode = CGDataMode::Write;
1567 // Create a local outlined hash tree to be published.
1568 LocalHashTree = std::make_unique<OutlinedHashTree>();
1569 // We don't need to read the outlined hash tree from the previous codegen
1570 } else if (cgdata::hasOutlinedHashTree(LibraryOptions))
1571 OutlinerMode = CGDataMode::Read;
1572}
1573
1574void MachineOutliner::emitOutlinedHashTree(Module &M) {
1575 assert(LocalHashTree);
1576 if (!LocalHashTree->empty()) {
1577 LLVM_DEBUG({
1578 dbgs() << "Emit outlined hash tree. Size: " << LocalHashTree->size()
1579 << "\n";
1580 });
1581 SmallVector<char> Buf;
1582 raw_svector_ostream OS(Buf);
1583
1584 OutlinedHashTreeRecord HTR(std::move(LocalHashTree));
1585 HTR.serialize(OS);
1586
1587 llvm::StringRef Data(Buf.data(), Buf.size());
1588 std::unique_ptr<MemoryBuffer> Buffer =
1589 MemoryBuffer::getMemBuffer(Data, "in-memory outlined hash tree", false);
1590
1591 Triple TT(M.getTargetTriple());
1593 M, *Buffer,
1594 getCodeGenDataSectionName(CG_outline, TT.getObjectFormat()));
1595 }
1596}
1597
1598bool MachineOutliner::runOnModule(Module &M) {
1599 if (skipModule(M))
1600 return false;
1601
1602 // Check if there's anything in the module. If it's empty, then there's
1603 // nothing to outline.
1604 if (M.empty())
1605 return false;
1606
1607 // Initialize the outliner mode.
1608 initializeOutlinerMode(M);
1609
1610 MMI = &getAnalysis<MachineModuleInfoWrapperPass>().getMMI();
1611 TM = &getAnalysis<TargetPassConfig>().getTM<TargetMachine>();
1612
1613 // Number to append to the current outlined function.
1614 unsigned OutlinedFunctionNum = 0;
1615
1616 OutlineRepeatedNum = 0;
1617 if (!doOutline(M, OutlinedFunctionNum))
1618 return false;
1619
1620 for (unsigned I = 0; I < OutlinerReruns; ++I) {
1621 OutlinedFunctionNum = 0;
1622 OutlineRepeatedNum++;
1623 if (!doOutline(M, OutlinedFunctionNum)) {
1624 LLVM_DEBUG({
1625 dbgs() << "Did not outline on iteration " << I + 2 << " out of "
1626 << OutlinerReruns + 1 << "\n";
1627 });
1628 break;
1629 }
1630 }
1631
1632 if (OutlinerMode == CGDataMode::Write)
1633 emitOutlinedHashTree(M);
1634
1635 return true;
1636}
1637
1638bool MachineOutliner::doOutline(Module &M, unsigned &OutlinedFunctionNum) {
1639 // If the user passed -enable-machine-outliner=always or
1640 // -enable-machine-outliner, the pass will run on all functions in the module.
1641 // Otherwise, if the target supports default outlining, it will run on all
1642 // functions deemed by the target to be worth outlining from by default. Tell
1643 // the user how the outliner is running.
1644 LLVM_DEBUG({
1645 dbgs() << "Machine Outliner: Running on ";
1646 switch (RunOutlinerMode) {
1647 case RunOutliner::AlwaysOutline:
1648 dbgs() << "all functions";
1649 break;
1650 case RunOutliner::OptimisticPGO:
1651 dbgs() << "optimistically cold functions";
1652 break;
1653 case RunOutliner::ConservativePGO:
1654 dbgs() << "conservatively cold functions";
1655 break;
1656 case RunOutliner::TargetDefault:
1657 dbgs() << "target-default functions";
1658 break;
1659 case RunOutliner::NeverOutline:
1660 llvm_unreachable("should not outline");
1661 }
1662 dbgs() << "\n";
1663 });
1664
1665 // If the user specifies that they want to outline from linkonceodrs, set
1666 // it here.
1667 OutlineFromLinkOnceODRs = EnableLinkOnceODROutlining;
1668 InstructionMapper Mapper(*MMI);
1669
1670 // Prepare instruction mappings for the suffix tree.
1671 populateMapper(Mapper, M);
1672 std::vector<std::unique_ptr<OutlinedFunction>> FunctionList;
1673
1674 // Find all of the outlining candidates.
1675 if (OutlinerMode == CGDataMode::Read)
1676 findGlobalCandidates(Mapper, FunctionList);
1677 else
1678 findCandidates(Mapper, FunctionList);
1679
1680 // If we've requested size remarks, then collect the MI counts of every
1681 // function before outlining, and the MI counts after outlining.
1682 // FIXME: This shouldn't be in the outliner at all; it should ultimately be
1683 // the pass manager's responsibility.
1684 // This could pretty easily be placed in outline instead, but because we
1685 // really ultimately *don't* want this here, it's done like this for now
1686 // instead.
1687
1688 // Check if we want size remarks.
1689 bool ShouldEmitSizeRemarks = M.shouldEmitInstrCountChangedRemark();
1690 StringMap<unsigned> FunctionToInstrCount;
1691 if (ShouldEmitSizeRemarks)
1692 initSizeRemarkInfo(M, FunctionToInstrCount);
1693
1694 // Outline each of the candidates and return true if something was outlined.
1695 bool OutlinedSomething =
1696 outline(M, FunctionList, Mapper, OutlinedFunctionNum);
1697
1698 // If we outlined something, we definitely changed the MI count of the
1699 // module. If we've asked for size remarks, then output them.
1700 // FIXME: This should be in the pass manager.
1701 if (ShouldEmitSizeRemarks && OutlinedSomething)
1702 emitInstrCountChangedRemark(M, FunctionToInstrCount);
1703
1704 LLVM_DEBUG({
1705 if (!OutlinedSomething)
1706 dbgs() << "Stopped outlining at iteration " << OutlineRepeatedNum
1707 << " because no changes were found.\n";
1708 });
1709
1710 return OutlinedSomething;
1711}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock & MBB
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
This file defines the DenseMap class.
#define DEBUG_TYPE
const HexagonInstrInfo * TII
IRTranslator LLVM IR MI
Module.h This file contains the declarations for the Module class.
This file implements the LivePhysRegs utility for tracking liveness of physical registers.
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
Machine Check Debug Module
===- MachineOptimizationRemarkEmitter.h - Opt Diagnostics -*- C++ -*-—===//
static cl::opt< bool > DisableGlobalOutlining("disable-global-outlining", cl::Hidden, cl::desc("Disable global outlining only by ignoring " "the codegen data generation or use"), cl::init(false))
static bool allowPGOOutlining(RunOutliner RunOutlinerMode, const ProfileSummaryInfo *PSI, const BlockFrequencyInfo *BFI, MachineBasicBlock &MBB)
static SmallVector< std::vector< Candidate > > partitionCandidatesByInputSection(std::vector< Candidate > &Candidates)
static cl::opt< unsigned > OutlinerBenefitThreshold("outliner-benefit-threshold", cl::init(1), cl::Hidden, cl::desc("The minimum size in bytes before an outlining candidate is accepted"))
static StringRef getCandidateInputSection(const Candidate &C)
static cl::opt< bool > OutlinerLeafDescendants("outliner-leaf-descendants", cl::init(true), cl::Hidden, cl::desc("Consider all leaf descendants of internal nodes of the suffix " "tree as candidates for outlining (if false, only leaf children " "are considered)"))
static cl::opt< bool > AppendContentHashToOutlinedName("append-content-hash-outlined-name", cl::Hidden, cl::desc("This appends the content hash to the globally outlined function " "name. It's beneficial for enhancing the precision of the stable " "hash and for ordering the outlined functions."), cl::init(true))
static stable_hash hashInstruction(const MachineInstr &MI)
static cl::opt< unsigned > OutlinerReruns("machine-outliner-reruns", cl::init(0), cl::Hidden, cl::desc("Number of times to rerun the outliner after the initial outline"))
Number of times to re-run the outliner.
static cl::opt< bool > EnableLinkOnceODROutlining("enable-linkonceodr-outlining", cl::Hidden, cl::desc("Enable the machine outliner on linkonceodr functions"), cl::init(false))
static SmallVector< MatchedEntry > getMatchedEntries(InstructionMapper &Mapper)
Contains all data structures shared between the outliner implemented in MachineOutliner....
Register Reg
Register const TargetRegisterInfo * TRI
Promote Memory to Register
Definition Mem2Reg.cpp:110
This is the interface to build a ModuleSummaryIndex for a module.
static Expected< Function * > createOutlinedFunction(OpenMPIRBuilder &OMPBuilder, IRBuilderBase &Builder, const OpenMPIRBuilder::TargetKernelDefaultAttrs &DefaultAttrs, StringRef FuncName, SmallVectorImpl< Value * > &Inputs, OpenMPIRBuilder::TargetBodyGenCallbackTy &CBFunc, OpenMPIRBuilder::TargetGenArgAccessorsCallbackTy &ArgAccessorFuncCB, DebugLoc OutlinedFnLoc)
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
Definition PassSupport.h:56
MachineRegisterInfo & MRI
Func MI getDebugLoc()))
This file defines the SmallSet class.
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
Target-Independent Code Generator Pass Configuration Options pass.
Value * RHS
Value * LHS
AnalysisUsage & addUsedIfAvailable()
Add the specified Pass class to the set of analyses used by this pass.
AnalysisUsage & addRequired()
AnalysisUsage & addPreserved()
Add the specified Pass class to the set of analyses preserved by this pass.
void setPreservesAll()
Set by analyses that do not transform their input at all.
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
Definition BasicBlock.h:206
BlockFrequencyInfo pass uses BlockFrequencyInfoImpl implementation to estimate IR basic block frequen...
LLVM_ABI std::optional< uint64_t > getBlockProfileCount(const BasicBlock *BB) const
Returns the estimated profile count of BB.
static LLVM_ABI DebugLoc getMergedLocation(DebugLoc LocA, DebugLoc LocB)
When two instructions are combined into a single instruction we also need to combine the original loc...
Definition DebugLoc.cpp:186
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Definition DenseMap.h:827
static Function * Create(FunctionType *Ty, LinkageTypes Linkage, unsigned AddrSpace, const Twine &N="", Module *M=nullptr)
Definition Function.h:169
bool hasFnAttribute(Attribute::AttrKind Kind) const
Return true if the function has the attribute.
Definition Function.cpp:731
StringRef getSection() const
Get the custom section of this global if it has one.
bool hasSection() const
Check if this global has a custom object file section.
@ InternalLinkage
Rename collisions when linking (static functions).
Definition GlobalValue.h:60
bool hasAddressTaken() const
Test whether this block is used as something other than the target of a terminator,...
LLVM_ABI DebugLoc findDebugLoc(instr_iterator MBBI)
Find the next valid DebugLoc starting at MBBI, skipping any debug instructions.
MachineInstrBundleIterator< MachineInstr, true > reverse_iterator
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
LLVM_ABI instr_iterator erase(instr_iterator I)
Remove an instruction from the instruction list and delete it.
MachineInstrBundleIterator< MachineInstr > iterator
LLVM_ABI StringRef getName() const
Return the name of the corresponding LLVM basic block, or an empty string.
unsigned getInstructionCount() const
Return the number of MachineInstrs in this MachineFunction.
unsigned addFrameInst(const MCCFIInstruction &Inst)
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
const std::vector< MCCFIInstruction > & getFrameInstructions() const
Returns a reference to a list of cfi instructions in the function's prologue.
StringRef getName() const
getName - Return the name of the corresponding LLVM function.
bool exposesReturnsTwice() const
exposesReturnsTwice - Returns true if the function calls setjmp or any other similar functions with a...
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
const MachineFunctionProperties & getProperties() const
Get the function properties.
const MachineBasicBlock & front() const
MachineBasicBlock * CreateMachineBasicBlock(const BasicBlock *BB=nullptr, std::optional< UniqueBBID > BBID=std::nullopt)
CreateMachineInstr - Allocate a new MachineInstr.
void insert(iterator MBBI, MachineBasicBlock *MBB)
const MachineInstrBuilder & addCFIIndex(unsigned CFIIndex) const
reverse_iterator getReverse() const
Get a reverse iterator to the same node.
Representation of each machine instruction.
bool isDebugInstr() const
LLVM_ABI void dropMemRefs(MachineFunction &MF)
Clear this MachineInstr's memory reference descriptor list.
LLVM_ABI const MachineFunction * getMF() const
Return the function that contains the basic block that this instruction belongs to.
bool isBundledWithSucc() const
Return true if this instruction is part of a bundle, and it is not the last instruction in the bundle...
LLVM_ABI void clearKillInfo()
Clears kill flags on all operands.
void setDebugLoc(DebugLoc DL)
Replace current source information with new such.
This class contains meta information specific to a module.
LLVM_ABI MachineFunction & getOrCreateMachineFunction(Function &F)
Returns the MachineFunction constructed for the IR function F.
LLVM_ABI MachineFunction * getMachineFunction(const Function &F) const
Returns the MachineFunction associated to IR function F if there is one, otherwise nullptr.
static MachineOperand CreateReg(Register Reg, bool isDef, bool isImp=false, bool isKill=false, bool isDead=false, bool isUndef=false, bool isEarlyClobber=false, unsigned SubReg=0, bool isDebug=false, bool isInternalRead=false, bool isRenamable=false)
Diagnostic information for missed-optimization remarks.
LLVM_ABI void freezeReservedRegs()
freezeReservedRegs - Called by the register allocator to freeze the set of reserved registers before ...
const TargetRegisterInfo * getTargetRegisterInfo() const
LLVM_ABI void getNameWithPrefix(raw_ostream &OS, const GlobalValue *GV, bool CannotUsePrivateLabel) const
Print the appropriate prefix and the specified global variable's name.
Definition Mangler.cpp:121
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:253
const HashNode * getRoot() const
Analysis providing profile information.
LLVM_ABI uint64_t getOrCompColdCountThreshold() const
Returns ColdCountThreshold if set.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
size_type count(const T &V) const
count - Return 1 if the element is in the set, 0 otherwise.
Definition SmallSet.h:176
bool erase(const T &V)
Definition SmallSet.h:200
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
Definition SmallSet.h:184
reference emplace_back(ArgTypes &&... Args)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
iterator end()
Definition StringMap.h:214
iterator find(StringRef Key)
Definition StringMap.h:227
Represent a constant reference to a string, i.e.
Definition StringRef.h:56
std::string str() const
Get the contents as an std::string.
Definition StringRef.h:222
constexpr bool empty() const
Check if the string is empty.
Definition StringRef.h:141
constexpr size_t size() const
Get the string size.
Definition StringRef.h:144
virtual size_t clearLinkerOptimizationHints(const SmallPtrSetImpl< MachineInstr * > &MIs) const
Remove all Linker Optimization Hints (LOH) associated with instructions in MIs and.
virtual const TargetInstrInfo * getInstrInfo() const
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition Twine.h:82
self_iterator getIterator()
Definition ilist_node.h:123
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ BasicBlock
Various leaf nodes.
Definition ISDOpcodes.h:83
constexpr MCPhysReg SP
SmallVector< const MachineInstr * > InstrList
const OutlinedHashTree * getOutlinedHashTree(const cl::LibraryOptionsContext &LibraryOptions)
bool hasOutlinedHashTree(const cl::LibraryOptionsContext &LibraryOptions)
bool emitCGData(const cl::LibraryOptionsContext &LibraryOptions)
initializer< Ty > init(const Ty &Val)
Add a small namespace to avoid name clashes with the classes used in the streaming interface.
DiagnosticInfoOptimizationBase::Argument NV
This is an optimization pass for GlobalISel generic memory operations.
@ Length
Definition DWP.cpp:577
void stable_sort(R &&Range)
Definition STLExtras.h:2132
auto find(R &&Range, const T &Val)
Provide wrappers to std::find which take ranges instead of having to pass begin/end explicitly.
Definition STLExtras.h:1781
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
void append_range(Container &C, Range &&R)
Wrapper function to append range R to container C.
Definition STLExtras.h:2224
uint64_t stable_hash
An opaque object representing a stable hash code.
LLVM_ABI stable_hash stableHashValue(const MachineOperand &MO, bool SourceQualifyLocalGlobals=false)
bool hasNItemsOrMore(IterTy &&Begin, IterTy &&End, unsigned N, Pred &&ShouldBeCounted=[](const decltype(*std::declval< IterTy >()) &) { return true;}, std::enable_if_t< !std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< std::remove_reference_t< decltype(Begin)> >::iterator_category >::value, void > *=nullptr)
Return true if the sequence [Begin, End) has N or more items.
Definition STLExtras.h:2654
auto reverse(ContainerTy &&C)
Definition STLExtras.h:408
UWTableKind
Definition CodeGen.h:362
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
IRBuilder(LLVMContext &, FolderTy, InserterTy) -> IRBuilder< FolderTy, InserterTy >
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
MachineBasicBlock::instr_iterator getBundleEnd(MachineBasicBlock::instr_iterator I)
Returns an iterator pointing beyond the bundle containing I.
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
auto instructionsWithoutDebug(IterT It, IterT End, bool SkipPseudoOp=true)
Construct a range iterator which begins at It and moves forwards until End is reached,...
LLVM_ABI ModulePass * createMachineOutlinerPass(RunOutliner RunOutlinerMode)
This pass performs outlining on machine instructions directly before printing assembly.
uint16_t MCPhysReg
An unsigned integer type large enough to represent all physical registers, but not necessarily virtua...
Definition MCRegister.h:21
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Count
Definition InstrProf.h:145
void erase_if(Container &C, UnaryPredicate P)
Provide a container algorithm similar to C++ Library Fundamentals v2's erase_if which is equivalent t...
Definition STLExtras.h:2208
stable_hash stable_hash_combine(ArrayRef< stable_hash > Buffer)
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 void addLiveIns(MachineBasicBlock &MBB, const LivePhysRegs &LiveRegs)
Adds registers contained in LiveRegs to the block live-in list of MBB.
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
#define MORE()
Definition regcomp.c:247
MatchedEntry()=delete
MatchedEntry(unsigned StartIdx, unsigned EndIdx, unsigned Count)
A HashNode is an entry in an OutlinedHashTree, holding a hash value and a collection of Successors (o...
std::optional< unsigned > Terminals
The number of terminals in the sequence ending at this node.
An individual sequence of instructions to be replaced with a call to an outlined function.
MachineFunction * getMF() const
The information necessary to create an outlined function for some class of candidate.