LLVM 23.0.0git
AArch64TargetMachine.cpp
Go to the documentation of this file.
1//===-- AArch64TargetMachine.cpp - Define TargetMachine for AArch64 -------===//
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//
10//===----------------------------------------------------------------------===//
11
13#include "AArch64.h"
16#include "AArch64MacroFusion.h"
17#include "AArch64Subtarget.h"
34#include "llvm/CodeGen/Passes.h"
37#include "llvm/IR/Attributes.h"
38#include "llvm/IR/Function.h"
40#include "llvm/MC/MCAsmInfo.h"
43#include "llvm/Pass.h"
55#include <memory>
56
57using namespace llvm;
58
59static cl::opt<bool> EnableCCMP("aarch64-enable-ccmp",
60 cl::desc("Enable the CCMP formation pass"),
61 cl::init(true), cl::Hidden);
62
63static cl::opt<bool>
64 EnableCondBrTuning("aarch64-enable-cond-br-tune",
65 cl::desc("Enable the conditional branch tuning pass"),
66 cl::init(true), cl::Hidden);
67
69 "aarch64-enable-copy-propagation",
70 cl::desc("Enable the copy propagation with AArch64 copy instr"),
71 cl::init(true), cl::Hidden);
72
73static cl::opt<bool> EnableMCR("aarch64-enable-mcr",
74 cl::desc("Enable the machine combiner pass"),
75 cl::init(true), cl::Hidden);
76
77static cl::opt<bool> EnableStPairSuppress("aarch64-enable-stp-suppress",
78 cl::desc("Suppress STP for AArch64"),
79 cl::init(true), cl::Hidden);
80
82 "aarch64-enable-simd-scalar",
83 cl::desc("Enable use of AdvSIMD scalar integer instructions"),
84 cl::init(false), cl::Hidden);
85
86static cl::opt<bool>
87 EnablePromoteConstant("aarch64-enable-promote-const",
88 cl::desc("Enable the promote constant pass"),
89 cl::init(true), cl::Hidden);
90
92 "aarch64-enable-collect-loh",
93 cl::desc("Enable the pass that emits the linker optimization hints (LOH)"),
94 cl::init(true), cl::Hidden);
95
96static cl::opt<bool>
97 EnableDeadRegisterElimination("aarch64-enable-dead-defs", cl::Hidden,
98 cl::desc("Enable the pass that removes dead"
99 " definitions and replaces stores to"
100 " them with stores to the zero"
101 " register"),
102 cl::init(true));
103
105 "aarch64-enable-copyelim",
106 cl::desc("Enable the redundant copy elimination pass"), cl::init(true),
107 cl::Hidden);
108
109static cl::opt<bool> EnableLoadStoreOpt("aarch64-enable-ldst-opt",
110 cl::desc("Enable the load/store pair"
111 " optimization pass"),
112 cl::init(true), cl::Hidden);
113
115 "aarch64-enable-atomic-cfg-tidy", cl::Hidden,
116 cl::desc("Run SimplifyCFG after expanding atomic operations"
117 " to make use of cmpxchg flow-based information"),
118 cl::init(true));
119
120static cl::opt<bool>
121EnableEarlyIfConversion("aarch64-enable-early-ifcvt", cl::Hidden,
122 cl::desc("Run early if-conversion"),
123 cl::init(true));
124
125static cl::opt<bool>
126 EnableCondOpt("aarch64-enable-condopt",
127 cl::desc("Enable the condition optimizer pass"),
128 cl::init(true), cl::Hidden);
129
130static cl::opt<bool>
131 EnableGEPOpt("aarch64-enable-gep-opt", cl::Hidden,
132 cl::desc("Enable optimizations on complex GEPs"),
133 cl::init(false));
134
135static cl::opt<bool>
136 EnableSelectOpt("aarch64-select-opt", cl::Hidden,
137 cl::desc("Enable select to branch optimizations"),
138 cl::init(true));
139
140static cl::opt<bool>
141 BranchRelaxation("aarch64-enable-branch-relax", cl::Hidden, cl::init(true),
142 cl::desc("Relax out of range conditional branches"));
143
145 "aarch64-enable-compress-jump-tables", cl::Hidden, cl::init(true),
146 cl::desc("Use smallest entry possible for jump tables"));
147
148// FIXME: Unify control over GlobalMerge.
150 EnableGlobalMerge("aarch64-enable-global-merge", cl::Hidden,
151 cl::desc("Enable the global merge pass"));
152
153static cl::opt<bool>
154 EnableLoopDataPrefetch("aarch64-enable-loop-data-prefetch", cl::Hidden,
155 cl::desc("Enable the loop data prefetch pass"),
156 cl::init(true));
157
159 "aarch64-enable-global-isel-at-O", cl::Hidden,
160 cl::desc("Enable GlobalISel at or below an opt level (-1 to disable)"),
161 cl::init(0));
162
163static cl::opt<bool>
164 EnableSVEIntrinsicOpts("aarch64-enable-sve-intrinsic-opts", cl::Hidden,
165 cl::desc("Enable SVE intrinsic opts"),
166 cl::init(true));
167
168static cl::opt<bool>
169 EnableSMEPeepholeOpt("enable-aarch64-sme-peephole-opt", cl::init(true),
171 cl::desc("Perform SME peephole optimization"));
172
173static cl::opt<bool> EnableFalkorHWPFFix("aarch64-enable-falkor-hwpf-fix",
174 cl::init(true), cl::Hidden);
175
176static cl::opt<bool>
177 EnableBranchTargets("aarch64-enable-branch-targets", cl::Hidden,
178 cl::desc("Enable the AArch64 branch target pass"),
179 cl::init(true));
180
182 "aarch64-sve-vector-bits-max",
183 cl::desc("Assume SVE vector registers are at most this big, "
184 "with zero meaning no maximum size is assumed."),
185 cl::init(0), cl::Hidden);
186
188 "aarch64-sve-vector-bits-min",
189 cl::desc("Assume SVE vector registers are at least this big, "
190 "with zero meaning no minimum size is assumed."),
191 cl::init(0), cl::Hidden);
192
194 "force-streaming",
195 cl::desc("Force the use of streaming code for all functions"),
196 cl::init(false), cl::Hidden);
197
199 "force-streaming-compatible",
200 cl::desc("Force the use of streaming-compatible code for all functions"),
201 cl::init(false), cl::Hidden);
202
204
206 "aarch64-enable-gisel-ldst-prelegal",
207 cl::desc("Enable GlobalISel's pre-legalizer load/store optimization pass"),
208 cl::init(true), cl::Hidden);
209
211 "aarch64-enable-gisel-ldst-postlegal",
212 cl::desc("Enable GlobalISel's post-legalizer load/store optimization pass"),
213 cl::init(false), cl::Hidden);
214
215static cl::opt<bool>
216 EnableSinkFold("aarch64-enable-sink-fold",
217 cl::desc("Enable sinking and folding of instruction copies"),
218 cl::init(true), cl::Hidden);
219
220static cl::opt<bool>
221 EnableMachinePipeliner("aarch64-enable-pipeliner",
222 cl::desc("Enable Machine Pipeliner for AArch64"),
223 cl::init(false), cl::Hidden);
224
225static cl::opt<bool>
226 EnableNewSMEABILowering("aarch64-new-sme-abi",
227 cl::desc("Enable new lowering for the SME ABI"),
228 cl::init(true), cl::Hidden);
229
231 "aarch64-srlt-mitigate-sr2r",
232 cl::desc("Enable SUBREG_TO_REG mitigation by adding 'implicit-def' for "
233 "super-regs when using Subreg Liveness Tracking"),
234 cl::init(true), cl::Hidden);
235
238 // Register the target.
244 auto &PR = *PassRegistry::getPassRegistry();
288}
289
291
292//===----------------------------------------------------------------------===//
293// AArch64 Lowering public interface.
294//===----------------------------------------------------------------------===//
295static std::unique_ptr<TargetLoweringObjectFile> createTLOF(const Triple &TT) {
296 if (TT.isOSBinFormatMachO())
297 return std::make_unique<AArch64_MachoTargetObjectFile>();
298 if (TT.isOSBinFormatCOFF())
299 return std::make_unique<AArch64_COFFTargetObjectFile>();
300
301 return std::make_unique<AArch64_ELFTargetObjectFile>();
302}
303
305 if (CPU.empty() && TT.isArm64e())
306 return "apple-a12";
307 return CPU;
308}
309
311 std::optional<Reloc::Model> RM) {
312 // AArch64 Darwin and Windows are always PIC.
313 if (TT.isOSDarwin() || TT.isOSWindows())
314 return Reloc::PIC_;
315 // On ELF platforms the default static relocation model has a smart enough
316 // linker to cope with referencing external symbols defined in a shared
317 // library. Hence DynamicNoPIC doesn't need to be promoted to PIC.
318 if (!RM || *RM == Reloc::DynamicNoPIC)
319 return Reloc::Static;
320 return *RM;
321}
322
323static CodeModel::Model
325 std::optional<CodeModel::Model> CM, bool JIT) {
326 if (CM) {
327 if (*CM != CodeModel::Small && *CM != CodeModel::Tiny &&
328 *CM != CodeModel::Large) {
330 "Only small, tiny and large code models are allowed on AArch64");
331 } else if (*CM == CodeModel::Tiny && !TT.isOSBinFormatELF()) {
332 report_fatal_error("tiny code model is only supported on ELF");
333 }
334 return *CM;
335 }
336 // The default MCJIT memory managers make no guarantees about where they can
337 // find an executable page; JITed code needs to be able to refer to globals
338 // no matter how far away they are.
339 // We should set the CodeModel::Small for Windows ARM64 in JIT mode,
340 // since with large code model LLVM generating 4 MOV instructions, and
341 // Windows doesn't support relocating these long branch (4 MOVs).
342 if (JIT && !TT.isOSWindows())
343 return CodeModel::Large;
344 return CodeModel::Small;
345}
346
347/// Create an AArch64 architecture model.
348///
350 StringRef CPU, StringRef FS,
351 const TargetOptions &Options,
352 std::optional<Reloc::Model> RM,
353 std::optional<CodeModel::Model> CM,
354 CodeGenOptLevel OL, bool JIT,
355 bool LittleEndian)
356 : CodeGenTargetMachineImpl(T, TT.computeDataLayout(), TT,
357 computeDefaultCPU(TT, CPU), FS, Options,
359 getEffectiveAArch64CodeModel(TT, CM, JIT), OL),
360 TLOF(createTLOF(getTargetTriple())), isLittle(LittleEndian),
361 UseNewSMEABILowering(EnableNewSMEABILowering) {
362 initAsmInfo();
363
364 if (TT.isOSBinFormatMachO()) {
365 this->Options.TrapUnreachable = true;
366 this->Options.NoTrapAfterNoreturn = true;
367 }
368
369 if (getMCAsmInfo()->usesWindowsCFI()) {
370 // Unwinding can get confused if the last instruction in an
371 // exception-handling region (function, funclet, try block, etc.)
372 // is a call.
373 //
374 // FIXME: We could elide the trap if the next instruction would be in
375 // the same region anyway.
376 this->Options.TrapUnreachable = true;
377 }
378
379 if (this->Options.TLSSize == 0) // default
380 this->Options.TLSSize = 24;
381 if ((getCodeModel() == CodeModel::Small ||
383 this->Options.TLSSize > 32)
384 // for the small (and kernel) code model, the maximum TLS size is 4GiB
385 this->Options.TLSSize = 32;
386 else if (getCodeModel() == CodeModel::Tiny && this->Options.TLSSize > 24)
387 // for the tiny code model, the maximum TLS size is 1MiB (< 16MiB)
388 this->Options.TLSSize = 24;
389
390 const bool TargetSupportsGISel =
391 TT.getArch() != Triple::aarch64_32 &&
392 TT.getEnvironment() != Triple::GNUILP32 &&
393 !(getCodeModel() == CodeModel::Large && TT.isOSBinFormatMachO());
394
395 const bool GlobalISelFlag =
397
398 // Enable GlobalISel at or below EnableGlobalISelAt0, unless this is
399 // MachO/CodeModel::Large, which GlobalISel does not support.
400 if (TargetSupportsGISel &&
401 (static_cast<int>(getOptLevel()) <= EnableGlobalISelAtO ||
402 (!GlobalISelFlag && !Options.EnableGlobalISel))) {
403 setGlobalISel(true);
405 }
406
407 // AArch64 supports the MachineOutliner.
408 setMachineOutliner(true);
409
410 // AArch64 supports default outlining behaviour.
412
413 // AArch64 supports the debug entry values.
415
416 // AArch64 supports fixing up the DWARF unwind information.
417 if (!getMCAsmInfo()->usesWindowsCFI())
418 setCFIFixup(true);
419}
420
424
426
427const AArch64Subtarget *
429 Attribute CPUAttr = F.getFnAttribute("target-cpu");
430 Attribute TuneAttr = F.getFnAttribute("tune-cpu");
431 Attribute FSAttr = F.getFnAttribute("target-features");
432
433 StringRef CPU = CPUAttr.isValid() ? CPUAttr.getValueAsString() : TargetCPU;
434 StringRef TuneCPU = TuneAttr.isValid() ? TuneAttr.getValueAsString() : CPU;
435 StringRef FS = FSAttr.isValid() ? FSAttr.getValueAsString() : TargetFS;
436 bool HasMinSize = F.hasMinSize();
437
438 bool IsStreaming = ForceStreaming ||
439 F.hasFnAttribute("aarch64_pstate_sm_enabled") ||
440 F.hasFnAttribute("aarch64_pstate_sm_body");
441 bool IsStreamingCompatible = ForceStreamingCompatible ||
442 F.hasFnAttribute("aarch64_pstate_sm_compatible");
443
444 unsigned MinSVEVectorSize = 0;
445 unsigned MaxSVEVectorSize = 0;
446 if (F.hasFnAttribute(Attribute::VScaleRange)) {
447 ConstantRange CR = getVScaleRange(&F, 64);
448 MinSVEVectorSize = CR.getUnsignedMin().getZExtValue() * 128;
449 MaxSVEVectorSize = CR.getUnsignedMax().getZExtValue() * 128;
450 } else {
451 MinSVEVectorSize = SVEVectorBitsMinOpt;
452 MaxSVEVectorSize = SVEVectorBitsMaxOpt;
453 }
454
455 assert(MinSVEVectorSize % 128 == 0 &&
456 "SVE requires vector length in multiples of 128!");
457 assert(MaxSVEVectorSize % 128 == 0 &&
458 "SVE requires vector length in multiples of 128!");
459 assert((MaxSVEVectorSize >= MinSVEVectorSize || MaxSVEVectorSize == 0) &&
460 "Minimum SVE vector size should not be larger than its maximum!");
461
462 // Sanitize user input in case of no asserts
463 if (MaxSVEVectorSize != 0) {
464 MinSVEVectorSize = std::min(MinSVEVectorSize, MaxSVEVectorSize);
465 MaxSVEVectorSize = std::max(MinSVEVectorSize, MaxSVEVectorSize);
466 }
467
469 raw_svector_ostream(Key) << "SVEMin" << MinSVEVectorSize << "SVEMax"
470 << MaxSVEVectorSize << "IsStreaming=" << IsStreaming
471 << "IsStreamingCompatible=" << IsStreamingCompatible
472 << CPU << TuneCPU << FS
473 << "HasMinSize=" << HasMinSize;
474
475 auto &I = SubtargetMap[Key];
476 if (!I) {
477 // This needs to be done before we create a new subtarget since any
478 // creation will depend on the TM and the code generation flags on the
479 // function that reside in TargetOptions.
481 I = std::make_unique<AArch64Subtarget>(
482 TargetTriple, CPU, TuneCPU, FS, *this, isLittle, MinSVEVectorSize,
483 MaxSVEVectorSize, IsStreaming, IsStreamingCompatible, HasMinSize,
485 }
486
487 if (IsStreaming && !I->hasSME())
488 reportFatalUsageError("streaming SVE functions require SME");
489
490 return I.get();
491}
492
495 const AArch64Subtarget &ST = C->MF->getSubtarget<AArch64Subtarget>();
497 DAG->addMutation(createLoadClusterDAGMutation(DAG->TII, DAG->TRI));
498 DAG->addMutation(createStoreClusterDAGMutation(DAG->TII, DAG->TRI));
499 if (ST.hasFusion())
500 DAG->addMutation(createAArch64MacroFusionDAGMutation());
501 return DAG;
502}
503
506 const AArch64Subtarget &ST = C->MF->getSubtarget<AArch64Subtarget>();
508 if (ST.hasFusion()) {
509 // Run the Macro Fusion after RA again since literals are expanded from
510 // pseudos then (v. addPreSched2()).
511 DAG->addMutation(createAArch64MacroFusionDAGMutation());
512 return DAG;
513 }
514
515 return DAG;
516}
517
519 const SmallPtrSetImpl<MachineInstr *> &MIs) const {
520 if (MIs.empty())
521 return 0;
522 auto *MI = *MIs.begin();
523 auto *FuncInfo = MI->getMF()->getInfo<AArch64FunctionInfo>();
524 return FuncInfo->clearLinkerOptimizationHints(MIs);
525}
526
527void AArch64leTargetMachine::anchor() { }
528
530 const Target &T, const Triple &TT, StringRef CPU, StringRef FS,
531 const TargetOptions &Options, std::optional<Reloc::Model> RM,
532 std::optional<CodeModel::Model> CM, CodeGenOptLevel OL, bool JIT)
533 : AArch64TargetMachine(T, TT, CPU, FS, Options, RM, CM, OL, JIT, true) {}
534
535void AArch64beTargetMachine::anchor() { }
536
538 const Target &T, const Triple &TT, StringRef CPU, StringRef FS,
539 const TargetOptions &Options, std::optional<Reloc::Model> RM,
540 std::optional<CodeModel::Model> CM, CodeGenOptLevel OL, bool JIT)
541 : AArch64TargetMachine(T, TT, CPU, FS, Options, RM, CM, OL, JIT, false) {}
542
543namespace {
544
545/// AArch64 Code Generator Pass Configuration Options.
546class AArch64PassConfig : public TargetPassConfig {
547public:
548 AArch64PassConfig(AArch64TargetMachine &TM, PassManagerBase &PM)
549 : TargetPassConfig(TM, PM) {
551 substitutePass(&PostRASchedulerID, &PostMachineSchedulerID);
552 setEnableSinkAndFold(EnableSinkFold);
553 }
554
555 AArch64TargetMachine &getAArch64TargetMachine() const {
557 }
558
559 void addIRPasses() override;
560 bool addPreISel() override;
561 void addCodeGenPrepare() override;
562 bool addInstSelector() override;
563 bool addIRTranslator() override;
564 void addPreLegalizeMachineIR() override;
565 bool addLegalizeMachineIR() override;
566 void addPreRegBankSelect() override;
567 bool addRegBankSelect() override;
568 bool addGlobalInstructionSelect() override;
569 void addMachineSSAOptimization() override;
570 bool addILPOpts() override;
571 void addPreRegAlloc() override;
572 void addPostRewrite() override;
573 void addPostRegAlloc() override;
574 void addPreSched2() override;
575 void addPreEmitPass() override;
576 void addPostBBSections() override;
577 void addPreEmitPass2() override;
578 bool addRegAssignAndRewriteOptimized() override;
579
580 std::unique_ptr<CSEConfigBase> getCSEConfig() const override;
581
582private:
583 bool isGlobalISelOptNone() const;
584};
585
586} // end anonymous namespace
587
589
590 PB.registerLateLoopOptimizationsEPCallback(
591 [=](LoopPassManager &LPM, OptimizationLevel Level) {
592 if (Level != OptimizationLevel::O0)
593 LPM.addPass(LoopIdiomVectorizePass());
594 });
595 if (getTargetTriple().isOSWindows())
596 PB.registerPipelineEarlySimplificationEPCallback(
599 });
600}
601
604 return TargetTransformInfo(std::make_unique<AArch64TTIImpl>(this, F));
605}
606
608 return new AArch64PassConfig(*this, PM);
609}
610
611std::unique_ptr<CSEConfigBase> AArch64PassConfig::getCSEConfig() const {
612 return getStandardCSEConfigForOpt(TM->getOptLevel());
613}
614
615// This function checks whether the opt level is explictly set to none,
616// or whether GlobalISel was enabled due to SDAG encountering an optnone
617// function. If the opt level is greater than the level we automatically enable
618// globalisel at, and it wasn't enabled via CLI, we know that it must be because
619// of an optnone function.
620bool AArch64PassConfig::isGlobalISelOptNone() const {
621 const bool GlobalISelFlag =
623
624 return getOptLevel() == CodeGenOptLevel::None ||
625 (static_cast<unsigned>(getOptLevel()) >
626 getAArch64TargetMachine().getEnableGlobalISelAtO() &&
627 !GlobalISelFlag);
628}
629
630void AArch64PassConfig::addIRPasses() {
631 // Always expand atomic operations, we don't deal with atomicrmw or cmpxchg
632 // ourselves.
634
635 // Expand any SVE vector library calls that we can't code generate directly.
637 TM->getOptLevel() != CodeGenOptLevel::None)
639
640 // Cmpxchg instructions are often used with a subsequent comparison to
641 // determine whether it succeeded. We can exploit existing control-flow in
642 // ldrex/strex loops to simplify this, but it needs tidying up.
643 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableAtomicTidy)
645 .forwardSwitchCondToPhi(true)
646 .convertSwitchRangeToICmp(true)
647 .convertSwitchToLookupTable(true)
648 .needCanonicalLoops(false)
649 .hoistCommonInsts(true)
650 .sinkCommonInsts(true)));
651
652 // Run LoopDataPrefetch
653 //
654 // Run this before LSR to remove the multiplies involved in computing the
655 // pointer values N iterations ahead.
656 if (TM->getOptLevel() != CodeGenOptLevel::None) {
661 }
662
663 if (EnableGEPOpt) {
664 // Call SeparateConstOffsetFromGEP pass to extract constants within indices
665 // and lower a GEP with multiple indices to either arithmetic operations or
666 // multiple GEPs with single index.
668 // Call EarlyCSE pass to find and remove subexpressions in the lowered
669 // result.
670 addPass(createEarlyCSEPass());
671 // Do loop invariant code motion in case part of the lowered result is
672 // invariant.
673 addPass(createLICMPass());
674 }
675
677
678 if (getOptLevel() == CodeGenOptLevel::Aggressive && EnableSelectOpt)
679 addPass(createSelectOptimizePass());
680
682 /*IsOptNone=*/TM->getOptLevel() == CodeGenOptLevel::None));
683
684 // Match complex arithmetic patterns
685 if (TM->getOptLevel() >= CodeGenOptLevel::Default)
687
688 // Match interleaved memory accesses to ldN/stN intrinsics.
689 if (TM->getOptLevel() != CodeGenOptLevel::None) {
692 }
693
695 // Expand any functions marked with SME attributes which require special
696 // changes for the calling convention or that require the lazy-saving
697 // mechanism specified in the SME ABI.
698 addPass(createSMEABIPass());
699 }
700
701 // Add Control Flow Guard checks.
702 if (TM->getTargetTriple().isOSWindows()) {
703 if (TM->getTargetTriple().isWindowsArm64EC())
705 else
706 addPass(createCFGuardCheckPass());
707 }
708
709 if (TM->Options.JMCInstrument)
710 addPass(createJMCInstrumenterPass());
711}
712
713// Pass Pipeline Configuration
714bool AArch64PassConfig::addPreISel() {
715 // Run promote constant before global merge, so that the promoted constants
716 // get a chance to be merged
717 if (TM->getOptLevel() != CodeGenOptLevel::None && EnablePromoteConstant)
719 // FIXME: On AArch64, this depends on the type.
720 // Basically, the addressable offsets are up to 4095 * Ty.getSizeInBytes().
721 // and the offset has to be a multiple of the related size in bytes.
722 if ((TM->getOptLevel() != CodeGenOptLevel::None &&
725 bool OnlyOptimizeForSize =
726 (TM->getOptLevel() < CodeGenOptLevel::Aggressive) &&
728
729 // Merging of extern globals is enabled by default on non-Mach-O as we
730 // expect it to be generally either beneficial or harmless. On Mach-O it
731 // is disabled as we emit the .subsections_via_symbols directive which
732 // means that merging extern globals is not safe.
733 bool MergeExternalByDefault = !TM->getTargetTriple().isOSBinFormatMachO();
734 addPass(createGlobalMergePass(TM, 4095, OnlyOptimizeForSize,
735 MergeExternalByDefault));
736 }
737
738 return false;
739}
740
741void AArch64PassConfig::addCodeGenPrepare() {
742 if (getOptLevel() != CodeGenOptLevel::None)
745}
746
747bool AArch64PassConfig::addInstSelector() {
748 addPass(createAArch64ISelDag(getAArch64TargetMachine(), getOptLevel()));
749
750 // For ELF, cleanup any local-dynamic TLS accesses (i.e. combine as many
751 // references to _TLS_MODULE_BASE_ as possible.
752 if (TM->getTargetTriple().isOSBinFormatELF() &&
753 getOptLevel() != CodeGenOptLevel::None)
755
756 return false;
757}
758
759bool AArch64PassConfig::addIRTranslator() {
760 addPass(new IRTranslator(getOptLevel()));
761 return false;
762}
763
764void AArch64PassConfig::addPreLegalizeMachineIR() {
765 if (isGlobalISelOptNone()) {
767 addPass(new Localizer());
768 } else {
770 addPass(new Localizer());
772 addPass(new LoadStoreOpt());
773 }
774}
775
776bool AArch64PassConfig::addLegalizeMachineIR() {
777 addPass(new Legalizer());
778 return false;
779}
780
781void AArch64PassConfig::addPreRegBankSelect() {
782 if (!isGlobalISelOptNone()) {
783 addPass(createAArch64PostLegalizerCombiner(isGlobalISelOptNone()));
785 addPass(new LoadStoreOpt());
786 }
788}
789
790bool AArch64PassConfig::addRegBankSelect() {
791 addPass(new RegBankSelect());
792 return false;
793}
794
795bool AArch64PassConfig::addGlobalInstructionSelect() {
796 addPass(new InstructionSelect(getOptLevel()));
797 if (!isGlobalISelOptNone())
799 return false;
800}
801
802void AArch64PassConfig::addMachineSSAOptimization() {
803 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableNewSMEABILowering)
804 addPass(createMachineSMEABIPass(TM->getOptLevel()));
805
806 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableSMEPeepholeOpt)
807 addPass(createSMEPeepholeOptPass());
808
809 // Run default MachineSSAOptimization first.
811
812 if (TM->getOptLevel() != CodeGenOptLevel::None)
814}
815
816bool AArch64PassConfig::addILPOpts() {
817 if (EnableCondOpt)
819 if (EnableCCMP)
821 if (EnableMCR)
822 addPass(&MachineCombinerID);
824 addPass(createAArch64CondBrTuning());
826 addPass(&EarlyIfConverterLegacyID);
830 if (TM->getOptLevel() != CodeGenOptLevel::None)
832 return true;
833}
834
835void AArch64PassConfig::addPreRegAlloc() {
836 if (TM->getOptLevel() == CodeGenOptLevel::None && EnableNewSMEABILowering)
838
839 // Change dead register definitions to refer to the zero register.
840 if (TM->getOptLevel() != CodeGenOptLevel::None &&
843
844 // Use AdvSIMD scalar instructions whenever profitable.
845 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableAdvSIMDScalar) {
847 // The AdvSIMD pass may produce copies that can be rewritten to
848 // be register coalescer friendly.
850 }
851 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableMachinePipeliner)
852 addPass(&MachinePipelinerID);
853}
854
855void AArch64PassConfig::addPostRewrite() {
858}
859
860void AArch64PassConfig::addPostRegAlloc() {
861 // Remove redundant copy instructions.
862 if (TM->getOptLevel() != CodeGenOptLevel::None &&
865
866 if (TM->getOptLevel() != CodeGenOptLevel::None && usingDefaultRegAlloc())
867 // Improve performance for some FP/SIMD code for A57.
869}
870
871void AArch64PassConfig::addPreSched2() {
872 // Lower homogeneous frame instructions
875 // Expand some pseudo instructions to allow proper scheduling.
877 // Use load/store pair instructions when possible.
878 if (TM->getOptLevel() != CodeGenOptLevel::None) {
881 }
882 // Emit KCFI checks for indirect calls.
883 addPass(createKCFIPass());
884
885 // The AArch64SpeculationHardeningPass destroys dominator tree and natural
886 // loop info, which is needed for the FalkorHWPFFixPass and also later on.
887 // Therefore, run the AArch64SpeculationHardeningPass before the
888 // FalkorHWPFFixPass to avoid recomputing dominator tree and natural loop
889 // info.
891
892 if (TM->getOptLevel() != CodeGenOptLevel::None) {
894 addPass(createFalkorHWPFFixPass());
895 }
896}
897
898void AArch64PassConfig::addPreEmitPass() {
899 // Machine Block Placement might have created new opportunities when run
900 // at O3, where the Tail Duplication Threshold is set to 4 instructions.
901 // Run the load/store optimizer once more.
902 if (TM->getOptLevel() >= CodeGenOptLevel::Aggressive && EnableLoadStoreOpt)
904
905 if (TM->getOptLevel() >= CodeGenOptLevel::Aggressive &&
908 if (TM->getOptLevel() != CodeGenOptLevel::None)
910
911 addPass(createAArch64A53Fix835769());
912
913 if (TM->getTargetTriple().isOSWindows()) {
914 // Identify valid longjmp targets for Windows Control Flow Guard.
915 addPass(createCFGuardLongjmpPass());
916 // Identify valid eh continuation targets for Windows EHCont Guard.
918 }
919
920 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableCollectLOH &&
921 TM->getTargetTriple().isOSBinFormatMachO())
923}
924
925void AArch64PassConfig::addPostBBSections() {
930 // Relax conditional branch instructions if they're otherwise out of
931 // range of their destination.
933 addPass(&BranchRelaxationPassID);
934
935 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableCompressJumpTables)
937}
938
939void AArch64PassConfig::addPreEmitPass2() {
940 // SVE bundles move prefixes with destructive operations. BLR_RVMARKER pseudo
941 // instructions are lowered to bundles as well.
942 addPass(createUnpackMachineBundles(nullptr));
943}
944
945bool AArch64PassConfig::addRegAssignAndRewriteOptimized() {
948}
949
956
961
964 const auto *MFI = MF.getInfo<AArch64FunctionInfo>();
965 return new yaml::AArch64FunctionInfo(*MFI);
966}
967
970 SMDiagnostic &Error, SMRange &SourceRange) const {
971 const auto &YamlMFI = static_cast<const yaml::AArch64FunctionInfo &>(MFI);
972 MachineFunction &MF = PFS.MF;
973 MF.getInfo<AArch64FunctionInfo>()->initializeBaseYamlFields(YamlMFI);
974 return false;
975}
cl::opt< bool > EnableHomogeneousPrologEpilog("homogeneous-prolog-epilog", cl::Hidden, cl::desc("Emit homogeneous prologue and epilogue for the size " "optimization (default = off)"))
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static cl::opt< bool > EnableBranchTargets("aarch64-enable-branch-targets", cl::Hidden, cl::desc("Enable the AArch64 branch target pass"), cl::init(true))
static cl::opt< bool > EnableSVEIntrinsicOpts("aarch64-enable-sve-intrinsic-opts", cl::Hidden, cl::desc("Enable SVE intrinsic opts"), cl::init(true))
static cl::opt< bool > EnableNewSMEABILowering("aarch64-new-sme-abi", cl::desc("Enable new lowering for the SME ABI"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableAArch64CopyPropagation("aarch64-enable-copy-propagation", cl::desc("Enable the copy propagation with AArch64 copy instr"), cl::init(true), cl::Hidden)
static cl::opt< bool > BranchRelaxation("aarch64-enable-branch-relax", cl::Hidden, cl::init(true), cl::desc("Relax out of range conditional branches"))
static cl::opt< bool > EnablePromoteConstant("aarch64-enable-promote-const", cl::desc("Enable the promote constant pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableCondBrTuning("aarch64-enable-cond-br-tune", cl::desc("Enable the conditional branch tuning pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableSinkFold("aarch64-enable-sink-fold", cl::desc("Enable sinking and folding of instruction copies"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableDeadRegisterElimination("aarch64-enable-dead-defs", cl::Hidden, cl::desc("Enable the pass that removes dead" " definitions and replaces stores to" " them with stores to the zero" " register"), cl::init(true))
static cl::opt< bool > EnableGEPOpt("aarch64-enable-gep-opt", cl::Hidden, cl::desc("Enable optimizations on complex GEPs"), cl::init(false))
static cl::opt< bool > EnableSelectOpt("aarch64-select-opt", cl::Hidden, cl::desc("Enable select to branch optimizations"), cl::init(true))
static cl::opt< bool > EnableLoadStoreOpt("aarch64-enable-ldst-opt", cl::desc("Enable the load/store pair" " optimization pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableGISelLoadStoreOptPostLegal("aarch64-enable-gisel-ldst-postlegal", cl::desc("Enable GlobalISel's post-legalizer load/store optimization pass"), cl::init(false), cl::Hidden)
static StringRef computeDefaultCPU(const Triple &TT, StringRef CPU)
static cl::opt< unsigned > SVEVectorBitsMinOpt("aarch64-sve-vector-bits-min", cl::desc("Assume SVE vector registers are at least this big, " "with zero meaning no minimum size is assumed."), cl::init(0), cl::Hidden)
static cl::opt< bool > EnableMCR("aarch64-enable-mcr", cl::desc("Enable the machine combiner pass"), cl::init(true), cl::Hidden)
static cl::opt< cl::boolOrDefault > EnableGlobalMerge("aarch64-enable-global-merge", cl::Hidden, cl::desc("Enable the global merge pass"))
static cl::opt< bool > EnableStPairSuppress("aarch64-enable-stp-suppress", cl::desc("Suppress STP for AArch64"), cl::init(true), cl::Hidden)
static CodeModel::Model getEffectiveAArch64CodeModel(const Triple &TT, std::optional< CodeModel::Model > CM, bool JIT)
static cl::opt< bool > EnableCondOpt("aarch64-enable-condopt", cl::desc("Enable the condition optimizer pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > ForceStreaming("force-streaming", cl::desc("Force the use of streaming code for all functions"), cl::init(false), cl::Hidden)
static cl::opt< bool > EnableCollectLOH("aarch64-enable-collect-loh", cl::desc("Enable the pass that emits the linker optimization hints (LOH)"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableGISelLoadStoreOptPreLegal("aarch64-enable-gisel-ldst-prelegal", cl::desc("Enable GlobalISel's pre-legalizer load/store optimization pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableRedundantCopyElimination("aarch64-enable-copyelim", cl::desc("Enable the redundant copy elimination pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableAtomicTidy("aarch64-enable-atomic-cfg-tidy", cl::Hidden, cl::desc("Run SimplifyCFG after expanding atomic operations" " to make use of cmpxchg flow-based information"), cl::init(true))
static cl::opt< bool > EnableAdvSIMDScalar("aarch64-enable-simd-scalar", cl::desc("Enable use of AdvSIMD scalar integer instructions"), cl::init(false), cl::Hidden)
static cl::opt< int > EnableGlobalISelAtO("aarch64-enable-global-isel-at-O", cl::Hidden, cl::desc("Enable GlobalISel at or below an opt level (-1 to disable)"), cl::init(0))
static cl::opt< bool > EnableLoopDataPrefetch("aarch64-enable-loop-data-prefetch", cl::Hidden, cl::desc("Enable the loop data prefetch pass"), cl::init(true))
static cl::opt< bool > EnableSMEPeepholeOpt("enable-aarch64-sme-peephole-opt", cl::init(true), cl::Hidden, cl::desc("Perform SME peephole optimization"))
static cl::opt< bool > EnableEarlyIfConversion("aarch64-enable-early-ifcvt", cl::Hidden, cl::desc("Run early if-conversion"), cl::init(true))
static cl::opt< bool > EnableSRLTSubregToRegMitigation("aarch64-srlt-mitigate-sr2r", cl::desc("Enable SUBREG_TO_REG mitigation by adding 'implicit-def' for " "super-regs when using Subreg Liveness Tracking"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableMachinePipeliner("aarch64-enable-pipeliner", cl::desc("Enable Machine Pipeliner for AArch64"), cl::init(false), cl::Hidden)
static cl::opt< bool > EnableFalkorHWPFFix("aarch64-enable-falkor-hwpf-fix", cl::init(true), cl::Hidden)
static cl::opt< unsigned > SVEVectorBitsMaxOpt("aarch64-sve-vector-bits-max", cl::desc("Assume SVE vector registers are at most this big, " "with zero meaning no maximum size is assumed."), cl::init(0), cl::Hidden)
static cl::opt< bool > ForceStreamingCompatible("force-streaming-compatible", cl::desc("Force the use of streaming-compatible code for all functions"), cl::init(false), cl::Hidden)
static std::unique_ptr< TargetLoweringObjectFile > createTLOF(const Triple &TT)
static cl::opt< bool > EnableCompressJumpTables("aarch64-enable-compress-jump-tables", cl::Hidden, cl::init(true), cl::desc("Use smallest entry possible for jump tables"))
LLVM_ABI LLVM_EXTERNAL_VISIBILITY void LLVMInitializeAArch64Target()
static cl::opt< bool > EnableCCMP("aarch64-enable-ccmp", cl::desc("Enable the CCMP formation pass"), cl::init(true), cl::Hidden)
This file a TargetTransformInfoImplBase conforming object specific to the AArch64 target machine.
static Reloc::Model getEffectiveRelocModel()
This file contains the simple types necessary to represent the attributes associated with functions a...
Provides analysis for continuously CSEing during GISel passes.
#define LLVM_ABI
Definition Compiler.h:213
#define LLVM_EXTERNAL_VISIBILITY
Definition Compiler.h:132
DXIL Legalizer
static cl::opt< bool > EnableGlobalMerge("enable-global-merge", cl::Hidden, cl::desc("Enable the global merge pass"), cl::init(true))
IRTranslator LLVM IR MI
This file declares the IRTranslator pass.
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
#define T
PassBuilder PB(Machine, PassOpts->PTO, std::nullopt, &PIC)
This file describes the interface of the MachineFunctionPass responsible for assigning the generic vi...
const GCNTargetMachine & getTM(const GCNSubtarget *STI)
static TableGen::Emitter::Opt Y("gen-skeleton-entry", EmitSkeleton, "Generate example skeleton entry")
static TableGen::Emitter::OptClass< SkeletonEmitter > X("gen-skeleton-class", "Generate example skeleton class")
Target-Independent Code Generator Pass Configuration Options pass.
This pass exposes codegen information to IR-level passes.
static std::unique_ptr< TargetLoweringObjectFile > createTLOF()
AArch64FunctionInfo - This class is derived from MachineFunctionInfo and contains private AArch64-spe...
size_t clearLinkerOptimizationHints(const SmallPtrSetImpl< MachineInstr * > &MIs)
size_t clearLinkerOptimizationHints(const SmallPtrSetImpl< MachineInstr * > &MIs) const override
Remove all Linker Optimization Hints (LOH) associated with instructions in MIs and.
StringMap< std::unique_ptr< AArch64Subtarget > > SubtargetMap
MachineFunctionInfo * createMachineFunctionInfo(BumpPtrAllocator &Allocator, const Function &F, const TargetSubtargetInfo *STI) const override
Create the target's instance of MachineFunctionInfo.
void registerPassBuilderCallbacks(PassBuilder &PB) override
Allow the target to modify the pass pipeline.
const AArch64Subtarget * getSubtargetImpl() const =delete
yaml::MachineFunctionInfo * createDefaultFuncInfoYAML() const override
Allocate and return a default initialized instance of the YAML representation for the MachineFunction...
ScheduleDAGInstrs * createPostMachineScheduler(MachineSchedContext *C) const override
Similar to createMachineScheduler but used when postRA machine scheduling is enabled.
unsigned getEnableGlobalISelAtO() const
Returns the optimisation level that enables GlobalISel.
std::unique_ptr< TargetLoweringObjectFile > TLOF
yaml::MachineFunctionInfo * convertFuncInfoToYAML(const MachineFunction &MF) const override
Allocate and initialize an instance of the YAML representation of the MachineFunctionInfo.
bool parseMachineFunctionInfo(const yaml::MachineFunctionInfo &, PerFunctionMIParsingState &PFS, SMDiagnostic &Error, SMRange &SourceRange) const override
Parse out the target's MachineFunctionInfo from the YAML reprsentation.
TargetPassConfig * createPassConfig(PassManagerBase &PM) override
Create a pass configuration object to be used by addPassToEmitX methods for generating a pipeline of ...
void reset() override
Reset internal state.
AArch64TargetMachine(const Target &T, const Triple &TT, StringRef CPU, StringRef FS, const TargetOptions &Options, std::optional< Reloc::Model > RM, std::optional< CodeModel::Model > CM, CodeGenOptLevel OL, bool JIT, bool IsLittleEndian)
Create an AArch64 architecture model.
ScheduleDAGInstrs * createMachineScheduler(MachineSchedContext *C) const override
Create an instance of ScheduleDAGInstrs to be run within the standard MachineScheduler pass for this ...
TargetTransformInfo getTargetTransformInfo(const Function &F) const override
Return a TargetTransformInfo for a given function.
AArch64beTargetMachine(const Target &T, const Triple &TT, StringRef CPU, StringRef FS, const TargetOptions &Options, std::optional< Reloc::Model > RM, std::optional< CodeModel::Model > CM, CodeGenOptLevel OL, bool JIT)
AArch64leTargetMachine(const Target &T, const Triple &TT, StringRef CPU, StringRef FS, const TargetOptions &Options, std::optional< Reloc::Model > RM, std::optional< CodeModel::Model > CM, CodeGenOptLevel OL, bool JIT)
uint64_t getZExtValue() const
Get zero extended value.
Definition APInt.h:1549
Functions, function parameters, and return types can have attributes to indicate how they should be t...
Definition Attributes.h:103
LLVM_ABI StringRef getValueAsString() const
Return the attribute's value as a string.
bool isValid() const
Return true if the attribute is any kind of attribute.
Definition Attributes.h:259
CodeGenTargetMachineImpl(const Target &T, StringRef DataLayoutString, const Triple &TT, StringRef CPU, StringRef FS, const TargetOptions &Options, Reloc::Model RM, CodeModel::Model CM, CodeGenOptLevel OL)
This class represents a range of values.
LLVM_ABI APInt getUnsignedMin() const
Return the smallest unsigned value contained in the ConstantRange.
LLVM_ABI APInt getUnsignedMax() const
Return the largest unsigned value contained in the ConstantRange.
Lightweight error class with error context and mandatory checking.
Definition Error.h:159
This pass is responsible for selecting generic machine instructions to target-specific instructions.
This pass implements the localization mechanism described at the top of this file.
Definition Localizer.h:43
Pass to replace calls to ifuncs with indirect calls.
Definition LowerIFunc.h:19
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
static LLVM_ABI const OptimizationLevel O0
Disable as many optimizations as possible.
This class provides access to building LLVM's passes.
LLVM_ATTRIBUTE_MINSIZE std::enable_if_t<!std::is_same_v< PassT, PassManager > > addPass(PassT &&Pass)
static LLVM_ABI PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
This pass implements the reg bank selector pass used in the GlobalISel pipeline.
Instances of this class encapsulate one diagnostic report, allowing printing to a raw_ostream as a ca...
Definition SourceMgr.h:297
Represents a range in source code.
Definition SMLoc.h:47
A ScheduleDAG for scheduling lists of MachineInstr.
ScheduleDAGMILive is an implementation of ScheduleDAGInstrs that schedules machine instructions while...
ScheduleDAGMI is an implementation of ScheduleDAGInstrs that simply schedules machine instructions ac...
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
iterator begin() const
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
Definition SmallString.h:26
StringRef - Represent a constant reference to a string, i.e.
Definition StringRef.h:55
CodeGenOptLevel getOptLevel() const
Returns the optimization level: None, Less, Default, or Aggressive.
void setSupportsDebugEntryValues(bool Enable)
Triple TargetTriple
Triple string, CPU name, and target feature strings the TargetMachine instance is created with.
const Triple & getTargetTriple() const
void setMachineOutliner(bool Enable)
void setCFIFixup(bool Enable)
void setSupportsDefaultOutlining(bool Enable)
void setGlobalISelAbort(GlobalISelAbortMode Mode)
std::unique_ptr< const MCSubtargetInfo > STI
void setGlobalISel(bool Enable)
TargetOptions Options
CodeModel::Model getCodeModel() const
Returns the code model.
void resetTargetOptions(const Function &F) const
Reset the target options based on the function's attributes.
const MCAsmInfo * getMCAsmInfo() const
Return target specific asm information.
unsigned TLSSize
Bit size of immediate TLS offsets (0 == use the default).
unsigned NoTrapAfterNoreturn
Do not emit a trap instruction for 'unreachable' IR instructions behind noreturn calls,...
unsigned TrapUnreachable
Emit target-specific trap instruction for 'unreachable' IR instructions.
Target-Independent Code Generator Pass Configuration Options.
virtual void addCodeGenPrepare()
Add pass to prepare the LLVM IR for code generation.
virtual void addIRPasses()
Add common target configurable passes that perform LLVM IR to IR transforms following machine indepen...
virtual void addMachineSSAOptimization()
addMachineSSAOptimization - Add standard passes that optimize machine instructions in SSA form.
virtual bool addRegAssignAndRewriteOptimized()
TargetSubtargetInfo - Generic base class for all target subtargets.
This pass provides access to the codegen interfaces that are needed for IR-level transformations.
Target - Wrapper for Target specific information.
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:47
PassManagerBase - An abstract interface to allow code to add passes to a pass manager without having ...
A raw_ostream that writes to an SmallVector or SmallString.
Interfaces for registering analysis passes, producing common pass manager configurations,...
@ C
The default llvm calling convention, compatible with C.
Definition CallingConv.h:34
@ DynamicNoPIC
Definition CodeGen.h:25
initializer< Ty > init(const Ty &Val)
This is an optimization pass for GlobalISel generic memory operations.
Definition Types.h:26
ScheduleDAGMILive * createSchedLive(MachineSchedContext *C)
Create the standard converging machine scheduler.
FunctionPass * createAArch64PreLegalizerCombiner()
void initializeLDTLSCleanupPass(PassRegistry &)
LLVM_ABI FunctionPass * createCFGSimplificationPass(SimplifyCFGOptions Options=SimplifyCFGOptions(), std::function< bool(const Function &)> Ftor=nullptr)
FunctionPass * createSMEABIPass()
void initializeAArch64A57FPLoadBalancingPass(PassRegistry &)
void initializeMachineSMEABIPass(PassRegistry &)
FunctionPass * createAArch64PostSelectOptimize()
LLVM_ABI ModulePass * createJMCInstrumenterPass()
JMC instrument pass.
void initializeAArch64SRLTDefineSuperRegsPass(PassRegistry &)
void initializeAArch64SpeculationHardeningPass(PassRegistry &)
void initializeAArch64PostLegalizerLoweringPass(PassRegistry &)
FunctionPass * createAArch64RedundantCopyEliminationPass()
FunctionPass * createAArch64StackTaggingPreRAPass()
LLVM_ABI FunctionPass * createTypePromotionLegacyPass()
Create IR Type Promotion pass.
void initializeAArch64PostLegalizerCombinerPass(PassRegistry &)
FunctionPass * createAArch64MIPeepholeOptPass()
void initializeAArch64AdvSIMDScalarPass(PassRegistry &)
void initializeAArch64PostCoalescerPass(PassRegistry &)
FunctionPass * createMachineSMEABIPass(CodeGenOptLevel)
LLVM_ABI FunctionPass * createSelectOptimizePass()
This pass converts conditional moves to conditional jumps when profitable.
LLVM_ABI Pass * createGlobalMergePass(const TargetMachine *TM, unsigned MaximalOffset, bool OnlyOptimizeForSize=false, bool MergeExternalByDefault=false, bool MergeConstantByDefault=false, bool MergeConstAggressiveByDefault=false)
GlobalMerge - This pass merges internal (by default) globals into structs to enable reuse of a base p...
FunctionPass * createAArch64PostCoalescerPass()
void initializeAArch64PromoteConstantPass(PassRegistry &)
FunctionPass * createFalkorMarkStridedAccessesPass()
Target & getTheAArch64beTarget()
FunctionPass * createAArch64PointerAuthPass()
FunctionPass * createFalkorHWPFFixPass()
void initializeAArch64RedundantCondBranchPass(PassRegistry &)
FunctionPass * createAArch64SRLTDefineSuperRegsPass()
LLVM_ABI char & PostRASchedulerID
PostRAScheduler - This pass performs post register allocation scheduling.
FunctionPass * createAArch64O0PreLegalizerCombiner()
FunctionPass * createAArch64A57FPLoadBalancing()
FunctionPass * createAArch64CondBrTuning()
LLVM_ABI std::unique_ptr< CSEConfigBase > getStandardCSEConfigForOpt(CodeGenOptLevel Level)
Definition CSEInfo.cpp:85
void initializeAArch64Arm64ECCallLoweringPass(PassRegistry &)
void initializeSMEABIPass(PassRegistry &)
LLVM_ABI char & PostMachineSchedulerID
PostMachineScheduler - This pass schedules machine instructions postRA.
LLVM_ABI char & PeepholeOptimizerLegacyID
PeepholeOptimizer - This pass performs peephole optimizations - like extension and comparison elimina...
LLVM_ABI Pass * createLICMPass()
Definition LICM.cpp:386
Target & getTheAArch64leTarget()
FunctionPass * createAArch64DeadRegisterDefinitions()
LLVM_ABI char & EarlyIfConverterLegacyID
EarlyIfConverter - This pass performs if-conversion on SSA form by inserting cmov instructions.
FunctionPass * createSMEPeepholeOptPass()
FunctionPass * createAArch64PostLegalizerLowering()
ThinOrFullLTOPhase
This enumerates the LLVM full LTO or ThinLTO optimization phases.
Definition Pass.h:77
PassManager< Loop, LoopAnalysisManager, LoopStandardAnalysisResults &, LPMUpdater & > LoopPassManager
The Loop pass manager.
LLVM_ABI char & MachineCombinerID
This pass performs instruction combining using trace metrics to estimate critical-path and resource d...
void initializeAArch64AsmPrinterPass(PassRegistry &)
static Reloc::Model getEffectiveRelocModel(std::optional< Reloc::Model > RM)
FunctionPass * createAArch64CompressJumpTablesPass()
Target & getTheAArch64_32Target()
FunctionPass * createAArch64ConditionalCompares()
ScheduleDAGMI * createSchedPostRA(MachineSchedContext *C)
Create a generic scheduler with no vreg liveness or DAG mutation passes.
LLVM_ABI char & BranchRelaxationPassID
BranchRelaxation - This pass replaces branches that need to jump further than is supported by a branc...
void initializeFalkorMarkStridedAccessesLegacyPass(PassRegistry &)
void initializeAArch64ExpandPseudoPass(PassRegistry &)
void initializeAArch64DeadRegisterDefinitionsPass(PassRegistry &)
void initializeAArch64StackTaggingPass(PassRegistry &)
FunctionPass * createAArch64ExpandPseudoPass()
Returns an instance of the pseudo instruction expansion pass.
LLVM_ABI FunctionPass * createKCFIPass()
Lowers KCFI operand bundles for indirect calls.
Definition KCFI.cpp:61
std::unique_ptr< ScheduleDAGMutation > createAArch64MacroFusionDAGMutation()
Note that you have to add: DAG.addMutation(createAArch64MacroFusionDAGMutation()); to AArch64TargetMa...
LLVM_ABI FunctionPass * createComplexDeinterleavingPass(const TargetMachine *TM)
This pass implements generation of target-specific intrinsics to support handling of complex number a...
PassManager< Module > ModulePassManager
Convenience typedef for a pass manager over modules.
ModulePass * createAArch64Arm64ECCallLoweringPass()
LLVM_ABI std::unique_ptr< ScheduleDAGMutation > createStoreClusterDAGMutation(const TargetInstrInfo *TII, const TargetRegisterInfo *TRI, bool ReorderWhileClustering=false)
If ReorderWhileClustering is set to true, no attempt will be made to reduce reordering due to store c...
LLVM_ABI FunctionPass * createLoopDataPrefetchPass()
FunctionPass * createAArch64SIMDInstrOptPass()
Returns an instance of the high cost ASIMD instruction replacement optimization pass.
void initializeSMEPeepholeOptPass(PassRegistry &)
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
FunctionPass * createAArch64StorePairSuppressPass()
FunctionPass * createAArch64ConditionOptimizerPass()
ModulePass * createSVEIntrinsicOptsPass()
void initializeAArch64CompressJumpTablesPass(PassRegistry &)
void initializeAArch64SLSHardeningPass(PassRegistry &)
FunctionPass * createAArch64CollectLOHPass()
LLVM_ABI ConstantRange getVScaleRange(const Function *F, unsigned BitWidth)
Determine the possible constant range of vscale with the given bit width, based on the vscale_range f...
CodeGenOptLevel
Code generation optimization level.
Definition CodeGen.h:82
@ Default
-O2, -Os, -Oz
Definition CodeGen.h:85
FunctionPass * createAArch64LoadStoreOptimizationPass()
createAArch64LoadStoreOptimizationPass - returns an instance of the load / store optimization pass.
void initializeAArch64StackTaggingPreRAPass(PassRegistry &)
LLVM_ABI FunctionPass * createCFGuardLongjmpPass()
Creates CFGuard longjmp target identification pass.
void initializeAArch64PreLegalizerCombinerPass(PassRegistry &)
LLVM_ATTRIBUTE_VISIBILITY_DEFAULT AnalysisKey InnerAnalysisManagerProxy< AnalysisManagerT, IRUnitT, ExtraArgTs... >::Key
Target & getTheARM64_32Target()
FunctionPass * createAArch64PostLegalizerCombiner(bool IsOptNone)
void initializeAArch64StorePairSuppressPass(PassRegistry &)
void initializeAArch64LowerHomogeneousPrologEpilogPass(PassRegistry &)
LLVM_ABI FunctionPass * createSeparateConstOffsetFromGEPPass(bool LowerGEP=false)
LLVM_ABI FunctionPass * createInterleavedAccessPass()
InterleavedAccess Pass - This pass identifies and matches interleaved memory accesses to target speci...
LLVM_ABI void initializeGlobalISel(PassRegistry &)
Initialize all passes linked into the GlobalISel library.
LLVM_ABI void initializeKCFIPass(PassRegistry &)
FunctionPass * createAArch64ISelDag(AArch64TargetMachine &TM, CodeGenOptLevel OptLevel)
createAArch64ISelDag - This pass converts a legalized DAG into a AArch64-specific DAG,...
void initializeAArch64CondBrTuningPass(PassRegistry &)
LLVM_ABI char & MachinePipelinerID
This pass performs software pipelining on machine instructions.
void initializeAArch64MIPeepholeOptPass(PassRegistry &)
FunctionPass * createAArch64SLSHardeningPass()
FunctionPass * createAArch64BranchTargetsPass()
Target & getTheARM64Target()
LLVM_ABI std::unique_ptr< ScheduleDAGMutation > createLoadClusterDAGMutation(const TargetInstrInfo *TII, const TargetRegisterInfo *TRI, bool ReorderWhileClustering=false)
If ReorderWhileClustering is set to true, no attempt will be made to reduce reordering due to store c...
void initializeFalkorHWPFFixPass(PassRegistry &)
LLVM_ABI FunctionPass * createUnpackMachineBundles(std::function< bool(const MachineFunction &)> Ftor)
void initializeAArch64BranchTargetsPass(PassRegistry &)
LLVM_ABI FunctionPass * createCFGuardCheckPass()
Insert Control FLow Guard checks on indirect function calls.
Definition CFGuard.cpp:306
void initializeAArch64A53Fix835769Pass(PassRegistry &)
LLVM_ABI FunctionPass * createEHContGuardTargetsPass()
Creates Windows EH Continuation Guard target identification pass.
ModulePass * createAArch64LowerHomogeneousPrologEpilogPass()
void initializeAArch64LoadStoreOptPass(PassRegistry &)
void initializeAArch64SIMDInstrOptPass(PassRegistry &)
void initializeAArch64PostSelectOptimizePass(PassRegistry &)
void initializeAArch64CollectLOHPass(PassRegistry &)
FunctionPass * createAArch64StackTaggingPass(bool IsOptNone)
void initializeAArch64O0PreLegalizerCombinerPass(PassRegistry &)
void initializeAArch64ConditionOptimizerPass(PassRegistry &)
void initializeAArch64ConditionalComparesPass(PassRegistry &)
LLVM_ABI FunctionPass * createAtomicExpandLegacyPass()
AtomicExpandPass - At IR level this pass replace atomic instructions with __atomic_* library calls,...
FunctionPass * createAArch64CleanupLocalDynamicTLSPass()
BumpPtrAllocatorImpl<> BumpPtrAllocator
The standard BumpPtrAllocator which just uses the default template parameters.
Definition Allocator.h:383
ModulePass * createAArch64PromoteConstantPass()
LLVM_ABI FunctionPass * createEarlyCSEPass(bool UseMemorySSA=false)
LLVM_ABI MachineFunctionPass * createMachineCopyPropagationPass(bool UseCopyInstr)
FunctionPass * createAArch64AdvSIMDScalar()
FunctionPass * createAArch64RedundantCondBranchPass()
void initializeAArch64DAGToDAGISelLegacyPass(PassRegistry &)
FunctionPass * createAArch64SpeculationHardeningPass()
Returns an instance of the pseudo instruction expansion pass.
void initializeSVEIntrinsicOptsPass(PassRegistry &)
void initializeAArch64PointerAuthPass(PassRegistry &)
void initializeAArch64RedundantCopyEliminationPass(PassRegistry &)
LLVM_ABI FunctionPass * createInterleavedLoadCombinePass()
InterleavedLoadCombines Pass - This pass identifies interleaved loads and combines them into wide loa...
FunctionPass * createAArch64A53Fix835769()
LLVM_ABI CGPassBuilderOption getCGPassBuilderOption()
LLVM_ABI void reportFatalUsageError(Error Err)
Report a fatal error that does not indicate a bug in LLVM.
Definition Error.cpp:177
std::optional< bool > EnableGlobalISelOption
MachineFunctionInfo - This class can be derived from and used by targets to hold private target-speci...
static FuncInfoTy * create(BumpPtrAllocator &Allocator, const Function &F, const SubtargetTy *STI)
Factory function: default behavior is to call new using the supplied allocator.
MachineSchedContext provides enough context from the MachineScheduler pass for the target to instanti...
RegisterTargetMachine - Helper template for registering a target machine implementation,...
Targets should override this in a way that mirrors the implementation of llvm::MachineFunctionInfo.