LLVM 20.0.0git
RISCVTargetMachine.cpp
Go to the documentation of this file.
1//===-- RISCVTargetMachine.cpp - Define TargetMachine for RISC-V ----------===//
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// Implements the info about RISC-V target spec.
10//
11//===----------------------------------------------------------------------===//
12
13#include "RISCVTargetMachine.h"
15#include "RISCV.h"
30#include "llvm/CodeGen/Passes.h"
38#include "llvm/Transforms/IPO.h"
41#include <optional>
42using namespace llvm;
43
45 "riscv-enable-copyelim",
46 cl::desc("Enable the redundant copy elimination pass"), cl::init(true),
48
49// FIXME: Unify control over GlobalMerge.
51 EnableGlobalMerge("riscv-enable-global-merge", cl::Hidden,
52 cl::desc("Enable the global merge pass"));
53
54static cl::opt<bool>
55 EnableMachineCombiner("riscv-enable-machine-combiner",
56 cl::desc("Enable the machine combiner pass"),
57 cl::init(true), cl::Hidden);
58
60 "riscv-v-vector-bits-max",
61 cl::desc("Assume V extension vector registers are at most this big, "
62 "with zero meaning no maximum size is assumed."),
64
66 "riscv-v-vector-bits-min",
67 cl::desc("Assume V extension vector registers are at least this big, "
68 "with zero meaning no minimum size is assumed. A value of -1 "
69 "means use Zvl*b extension. This is primarily used to enable "
70 "autovectorization with fixed width vectors."),
71 cl::init(-1), cl::Hidden);
72
74 "riscv-enable-copy-propagation",
75 cl::desc("Enable the copy propagation with RISC-V copy instr"),
76 cl::init(true), cl::Hidden);
77
79 "riscv-enable-dead-defs", cl::Hidden,
80 cl::desc("Enable the pass that removes dead"
81 " definitons and replaces stores to"
82 " them with stores to x0"),
83 cl::init(true));
84
85static cl::opt<bool>
86 EnableSinkFold("riscv-enable-sink-fold",
87 cl::desc("Enable sinking and folding of instruction copies"),
88 cl::init(true), cl::Hidden);
89
90static cl::opt<bool>
91 EnableLoopDataPrefetch("riscv-enable-loop-data-prefetch", cl::Hidden,
92 cl::desc("Enable the loop data prefetch pass"),
93 cl::init(true));
94
96 "riscv-misched-load-store-clustering", cl::Hidden,
97 cl::desc("Enable load and store clustering in the machine scheduler"),
98 cl::init(true));
99
101 "riscv-postmisched-load-store-clustering", cl::Hidden,
102 cl::desc("Enable PostRA load and store clustering in the machine scheduler"),
103 cl::init(true));
104
105static cl::opt<bool>
106 EnableVLOptimizer("riscv-enable-vl-optimizer",
107 cl::desc("Enable the RISC-V VL Optimizer pass"),
108 cl::init(true), cl::Hidden);
109
111 "riscv-disable-vector-mask-mutation",
112 cl::desc("Disable the vector mask scheduling mutation"), cl::init(false),
113 cl::Hidden);
114
115static cl::opt<bool>
116 EnableMachinePipeliner("riscv-enable-pipeliner",
117 cl::desc("Enable Machine Pipeliner for RISC-V"),
118 cl::init(false), cl::Hidden);
119
146}
147
149 const TargetOptions &Options) {
150 StringRef ABIName = Options.MCOptions.getABIName();
151 if (TT.isArch64Bit()) {
152 if (ABIName == "lp64e")
153 return "e-m:e-p:64:64-i64:64-i128:128-n32:64-S64";
154
155 return "e-m:e-p:64:64-i64:64-i128:128-n32:64-S128";
156 }
157 assert(TT.isArch32Bit() && "only RV32 and RV64 are currently supported");
158
159 if (ABIName == "ilp32e")
160 return "e-m:e-p:32:32-i64:64-n32-S32";
161
162 return "e-m:e-p:32:32-i64:64-n32-S128";
163}
164
166 std::optional<Reloc::Model> RM) {
167 return RM.value_or(Reloc::Static);
168}
169
171 StringRef CPU, StringRef FS,
172 const TargetOptions &Options,
173 std::optional<Reloc::Model> RM,
174 std::optional<CodeModel::Model> CM,
175 CodeGenOptLevel OL, bool JIT)
178 getEffectiveCodeModel(CM, CodeModel::Small), OL),
179 TLOF(std::make_unique<RISCVELFTargetObjectFile>()) {
180 initAsmInfo();
181
182 // RISC-V supports the MachineOutliner.
183 setMachineOutliner(true);
185
186 if (TT.isOSFuchsia() && !TT.isArch64Bit())
187 report_fatal_error("Fuchsia is only supported for 64-bit");
188
189 setCFIFixup(true);
190}
191
192const RISCVSubtarget *
194 Attribute CPUAttr = F.getFnAttribute("target-cpu");
195 Attribute TuneAttr = F.getFnAttribute("tune-cpu");
196 Attribute FSAttr = F.getFnAttribute("target-features");
197
198 std::string CPU =
199 CPUAttr.isValid() ? CPUAttr.getValueAsString().str() : TargetCPU;
200 std::string TuneCPU =
201 TuneAttr.isValid() ? TuneAttr.getValueAsString().str() : CPU;
202 std::string FS =
203 FSAttr.isValid() ? FSAttr.getValueAsString().str() : TargetFS;
204
205 unsigned RVVBitsMin = RVVVectorBitsMinOpt;
206 unsigned RVVBitsMax = RVVVectorBitsMaxOpt;
207
208 Attribute VScaleRangeAttr = F.getFnAttribute(Attribute::VScaleRange);
209 if (VScaleRangeAttr.isValid()) {
210 if (!RVVVectorBitsMinOpt.getNumOccurrences())
211 RVVBitsMin = VScaleRangeAttr.getVScaleRangeMin() * RISCV::RVVBitsPerBlock;
212 std::optional<unsigned> VScaleMax = VScaleRangeAttr.getVScaleRangeMax();
213 if (VScaleMax.has_value() && !RVVVectorBitsMaxOpt.getNumOccurrences())
214 RVVBitsMax = *VScaleMax * RISCV::RVVBitsPerBlock;
215 }
216
217 if (RVVBitsMin != -1U) {
218 // FIXME: Change to >= 32 when VLEN = 32 is supported.
219 assert((RVVBitsMin == 0 || (RVVBitsMin >= 64 && RVVBitsMin <= 65536 &&
220 isPowerOf2_32(RVVBitsMin))) &&
221 "V or Zve* extension requires vector length to be in the range of "
222 "64 to 65536 and a power 2!");
223 assert((RVVBitsMax >= RVVBitsMin || RVVBitsMax == 0) &&
224 "Minimum V extension vector length should not be larger than its "
225 "maximum!");
226 }
227 assert((RVVBitsMax == 0 || (RVVBitsMax >= 64 && RVVBitsMax <= 65536 &&
228 isPowerOf2_32(RVVBitsMax))) &&
229 "V or Zve* extension requires vector length to be in the range of "
230 "64 to 65536 and a power 2!");
231
232 if (RVVBitsMin != -1U) {
233 if (RVVBitsMax != 0) {
234 RVVBitsMin = std::min(RVVBitsMin, RVVBitsMax);
235 RVVBitsMax = std::max(RVVBitsMin, RVVBitsMax);
236 }
237
238 RVVBitsMin = llvm::bit_floor(
239 (RVVBitsMin < 64 || RVVBitsMin > 65536) ? 0 : RVVBitsMin);
240 }
241 RVVBitsMax =
242 llvm::bit_floor((RVVBitsMax < 64 || RVVBitsMax > 65536) ? 0 : RVVBitsMax);
243
245 raw_svector_ostream(Key) << "RVVMin" << RVVBitsMin << "RVVMax" << RVVBitsMax
246 << CPU << TuneCPU << FS;
247 auto &I = SubtargetMap[Key];
248 if (!I) {
249 // This needs to be done before we create a new subtarget since any
250 // creation will depend on the TM and the code generation flags on the
251 // function that reside in TargetOptions.
253 auto ABIName = Options.MCOptions.getABIName();
254 if (const MDString *ModuleTargetABI = dyn_cast_or_null<MDString>(
255 F.getParent()->getModuleFlag("target-abi"))) {
256 auto TargetABI = RISCVABI::getTargetABI(ABIName);
257 if (TargetABI != RISCVABI::ABI_Unknown &&
258 ModuleTargetABI->getString() != ABIName) {
259 report_fatal_error("-target-abi option != target-abi module flag");
260 }
261 ABIName = ModuleTargetABI->getString();
262 }
263 I = std::make_unique<RISCVSubtarget>(
264 TargetTriple, CPU, TuneCPU, FS, ABIName, RVVBitsMin, RVVBitsMax, *this);
265 }
266 return I.get();
267}
268
270 BumpPtrAllocator &Allocator, const Function &F,
271 const TargetSubtargetInfo *STI) const {
272 return RISCVMachineFunctionInfo::create<RISCVMachineFunctionInfo>(
273 Allocator, F, static_cast<const RISCVSubtarget *>(STI));
274}
275
278 return TargetTransformInfo(RISCVTTIImpl(this, F));
279}
280
281// A RISC-V hart has a single byte-addressable address space of 2^XLEN bytes
282// for all memory accesses, so it is reasonable to assume that an
283// implementation has no-op address space casts. If an implementation makes a
284// change to this, they can override it here.
286 unsigned DstAS) const {
287 return true;
288}
289
290namespace {
291
292class RVVRegisterRegAlloc : public RegisterRegAllocBase<RVVRegisterRegAlloc> {
293public:
294 RVVRegisterRegAlloc(const char *N, const char *D, FunctionPassCtor C)
295 : RegisterRegAllocBase(N, D, C) {}
296};
297
298static bool onlyAllocateRVVReg(const TargetRegisterInfo &TRI,
300 const Register Reg) {
301 const TargetRegisterClass *RC = MRI.getRegClass(Reg);
303}
304
305static FunctionPass *useDefaultRegisterAllocator() { return nullptr; }
306
307static llvm::once_flag InitializeDefaultRVVRegisterAllocatorFlag;
308
309/// -riscv-rvv-regalloc=<fast|basic|greedy> command line option.
310/// This option could designate the rvv register allocator only.
311/// For example: -riscv-rvv-regalloc=basic
312static cl::opt<RVVRegisterRegAlloc::FunctionPassCtor, false,
314 RVVRegAlloc("riscv-rvv-regalloc", cl::Hidden,
316 cl::desc("Register allocator to use for RVV register."));
317
318static void initializeDefaultRVVRegisterAllocatorOnce() {
319 RegisterRegAlloc::FunctionPassCtor Ctor = RVVRegisterRegAlloc::getDefault();
320
321 if (!Ctor) {
322 Ctor = RVVRegAlloc;
323 RVVRegisterRegAlloc::setDefault(RVVRegAlloc);
324 }
325}
326
327static FunctionPass *createBasicRVVRegisterAllocator() {
328 return createBasicRegisterAllocator(onlyAllocateRVVReg);
329}
330
331static FunctionPass *createGreedyRVVRegisterAllocator() {
332 return createGreedyRegisterAllocator(onlyAllocateRVVReg);
333}
334
335static FunctionPass *createFastRVVRegisterAllocator() {
336 return createFastRegisterAllocator(onlyAllocateRVVReg, false);
337}
338
339static RVVRegisterRegAlloc basicRegAllocRVVReg("basic",
340 "basic register allocator",
341 createBasicRVVRegisterAllocator);
342static RVVRegisterRegAlloc
343 greedyRegAllocRVVReg("greedy", "greedy register allocator",
344 createGreedyRVVRegisterAllocator);
345
346static RVVRegisterRegAlloc fastRegAllocRVVReg("fast", "fast register allocator",
347 createFastRVVRegisterAllocator);
348
349class RISCVPassConfig : public TargetPassConfig {
350public:
351 RISCVPassConfig(RISCVTargetMachine &TM, PassManagerBase &PM)
352 : TargetPassConfig(TM, PM) {
353 if (TM.getOptLevel() != CodeGenOptLevel::None)
354 substitutePass(&PostRASchedulerID, &PostMachineSchedulerID);
355 setEnableSinkAndFold(EnableSinkFold);
356 EnableLoopTermFold = true;
357 }
358
359 RISCVTargetMachine &getRISCVTargetMachine() const {
360 return getTM<RISCVTargetMachine>();
361 }
362
364 createMachineScheduler(MachineSchedContext *C) const override {
365 ScheduleDAGMILive *DAG = nullptr;
369 DAG->TII, DAG->TRI, /*ReorderWhileClustering=*/true));
371 DAG->TII, DAG->TRI, /*ReorderWhileClustering=*/true));
372 }
373
374 const RISCVSubtarget &ST = C->MF->getSubtarget<RISCVSubtarget>();
375 if (!DisableVectorMaskMutation && ST.hasVInstructions()) {
376 DAG = DAG ? DAG : createGenericSchedLive(C);
378 }
379 return DAG;
380 }
381
383 createPostMachineScheduler(MachineSchedContext *C) const override {
384 ScheduleDAGMI *DAG = nullptr;
388 DAG->TII, DAG->TRI, /*ReorderWhileClustering=*/true));
390 DAG->TII, DAG->TRI, /*ReorderWhileClustering=*/true));
391 }
392 return DAG;
393 }
394
395 void addIRPasses() override;
396 bool addPreISel() override;
397 void addCodeGenPrepare() override;
398 bool addInstSelector() override;
399 bool addIRTranslator() override;
400 void addPreLegalizeMachineIR() override;
401 bool addLegalizeMachineIR() override;
402 void addPreRegBankSelect() override;
403 bool addRegBankSelect() override;
404 bool addGlobalInstructionSelect() override;
405 void addPreEmitPass() override;
406 void addPreEmitPass2() override;
407 void addPreSched2() override;
408 void addMachineSSAOptimization() override;
409 FunctionPass *createRVVRegAllocPass(bool Optimized);
410 bool addRegAssignAndRewriteFast() override;
411 bool addRegAssignAndRewriteOptimized() override;
412 void addPreRegAlloc() override;
413 void addPostRegAlloc() override;
414 void addFastRegAlloc() override;
415
416 std::unique_ptr<CSEConfigBase> getCSEConfig() const override;
417};
418} // namespace
419
421 return new RISCVPassConfig(*this, PM);
422}
423
424std::unique_ptr<CSEConfigBase> RISCVPassConfig::getCSEConfig() const {
425 return getStandardCSEConfigForOpt(TM->getOptLevel());
426}
427
428FunctionPass *RISCVPassConfig::createRVVRegAllocPass(bool Optimized) {
429 // Initialize the global default.
430 llvm::call_once(InitializeDefaultRVVRegisterAllocatorFlag,
431 initializeDefaultRVVRegisterAllocatorOnce);
432
433 RegisterRegAlloc::FunctionPassCtor Ctor = RVVRegisterRegAlloc::getDefault();
434 if (Ctor != useDefaultRegisterAllocator)
435 return Ctor();
436
437 if (Optimized)
438 return createGreedyRVVRegisterAllocator();
439
440 return createFastRVVRegisterAllocator();
441}
442
443bool RISCVPassConfig::addRegAssignAndRewriteFast() {
444 addPass(createRVVRegAllocPass(false));
446 if (TM->getOptLevel() != CodeGenOptLevel::None &&
450}
451
452bool RISCVPassConfig::addRegAssignAndRewriteOptimized() {
453 addPass(createRVVRegAllocPass(true));
454 addPass(createVirtRegRewriter(false));
456 if (TM->getOptLevel() != CodeGenOptLevel::None &&
460}
461
462void RISCVPassConfig::addIRPasses() {
465
466 if (getOptLevel() != CodeGenOptLevel::None) {
469
473 }
474
476}
477
478bool RISCVPassConfig::addPreISel() {
479 if (TM->getOptLevel() != CodeGenOptLevel::None) {
480 // Add a barrier before instruction selection so that we will not get
481 // deleted block address after enabling default outlining. See D99707 for
482 // more details.
483 addPass(createBarrierNoopPass());
484 }
485
486 if ((TM->getOptLevel() != CodeGenOptLevel::None &&
489 // FIXME: Like AArch64, we disable extern global merging by default due to
490 // concerns it might regress some workloads. Unlike AArch64, we don't
491 // currently support enabling the pass in an "OnlyOptimizeForSize" mode.
492 // Investigating and addressing both items are TODO.
493 addPass(createGlobalMergePass(TM, /* MaxOffset */ 2047,
494 /* OnlyOptimizeForSize */ false,
495 /* MergeExternalByDefault */ true));
496 }
497
498 return false;
499}
500
501void RISCVPassConfig::addCodeGenPrepare() {
502 if (getOptLevel() != CodeGenOptLevel::None)
505}
506
507bool RISCVPassConfig::addInstSelector() {
508 addPass(createRISCVISelDag(getRISCVTargetMachine(), getOptLevel()));
509
510 return false;
511}
512
513bool RISCVPassConfig::addIRTranslator() {
514 addPass(new IRTranslator(getOptLevel()));
515 return false;
516}
517
518void RISCVPassConfig::addPreLegalizeMachineIR() {
519 if (getOptLevel() == CodeGenOptLevel::None) {
521 } else {
523 }
524}
525
526bool RISCVPassConfig::addLegalizeMachineIR() {
527 addPass(new Legalizer());
528 return false;
529}
530
531void RISCVPassConfig::addPreRegBankSelect() {
532 if (getOptLevel() != CodeGenOptLevel::None)
534}
535
536bool RISCVPassConfig::addRegBankSelect() {
537 addPass(new RegBankSelect());
538 return false;
539}
540
541bool RISCVPassConfig::addGlobalInstructionSelect() {
542 addPass(new InstructionSelect(getOptLevel()));
543 return false;
544}
545
546void RISCVPassConfig::addPreSched2() {
548
549 // Emit KCFI checks for indirect calls.
550 addPass(createKCFIPass());
551}
552
553void RISCVPassConfig::addPreEmitPass() {
554 // TODO: It would potentially be better to schedule copy propagation after
555 // expanding pseudos (in addPreEmitPass2). However, performing copy
556 // propagation after the machine outliner (which runs after addPreEmitPass)
557 // currently leads to incorrect code-gen, where copies to registers within
558 // outlined functions are removed erroneously.
559 if (TM->getOptLevel() >= CodeGenOptLevel::Default &&
562 addPass(&BranchRelaxationPassID);
564}
565
566void RISCVPassConfig::addPreEmitPass2() {
567 if (TM->getOptLevel() != CodeGenOptLevel::None) {
568 addPass(createRISCVMoveMergePass());
569 // Schedule PushPop Optimization before expansion of Pseudo instruction,
570 // ensuring return instruction is detected correctly.
572 }
575
576 // Schedule the expansion of AMOs at the last possible moment, avoiding the
577 // possibility for other passes to break the requirements for forward
578 // progress in the LR/SC block.
580
581 // KCFI indirect call checks are lowered to a bundle.
582 addPass(createUnpackMachineBundles([&](const MachineFunction &MF) {
583 return MF.getFunction().getParent()->getModuleFlag("kcfi");
584 }));
585}
586
587void RISCVPassConfig::addMachineSSAOptimization() {
589
591
593 addPass(&MachineCombinerID);
594
595 if (TM->getTargetTriple().isRISCV64()) {
596 addPass(createRISCVOptWInstrsPass());
597 }
598}
599
600void RISCVPassConfig::addPreRegAlloc() {
602 if (TM->getOptLevel() != CodeGenOptLevel::None) {
606 }
607
611
612 if (TM->getOptLevel() != CodeGenOptLevel::None && EnableMachinePipeliner)
613 addPass(&MachinePipelinerID);
614}
615
616void RISCVPassConfig::addFastRegAlloc() {
617 addPass(&InitUndefID);
619}
620
621
622void RISCVPassConfig::addPostRegAlloc() {
623 if (TM->getOptLevel() != CodeGenOptLevel::None &&
626}
627
630 OptimizationLevel Level) {
632 });
633}
634
638}
639
642 const auto *MFI = MF.getInfo<RISCVMachineFunctionInfo>();
643 return new yaml::RISCVMachineFunctionInfo(*MFI);
644}
645
648 SMDiagnostic &Error, SMRange &SourceRange) const {
649 const auto &YamlMFI =
650 static_cast<const yaml::RISCVMachineFunctionInfo &>(MFI);
651 PFS.MF.getInfo<RISCVMachineFunctionInfo>()->initializeBaseYamlFields(YamlMFI);
652 return false;
653}
unsigned const MachineRegisterInfo * MRI
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 > EnableRedundantCopyElimination("aarch64-enable-copyelim", cl::desc("Enable the redundant copy elimination pass"), cl::init(true), cl::Hidden)
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 > EnableMachinePipeliner("aarch64-enable-pipeliner", cl::desc("Enable Machine Pipeliner for AArch64"), cl::init(false), cl::Hidden)
static const Function * getParent(const Value *V)
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
Provides analysis for continuously CSEing during GISel passes.
#define LLVM_EXTERNAL_VISIBILITY
Definition: Compiler.h:128
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
static cl::opt< bool > EnableGlobalMerge("enable-global-merge", cl::Hidden, cl::desc("Enable the global merge pass"), cl::init(true))
This file declares the IRTranslator pass.
static LVOptions Options
Definition: LVOptions.cpp:25
static std::string computeDataLayout()
#define F(x, y, z)
Definition: MD5.cpp:55
#define I(x, y, z)
Definition: MD5.cpp:58
unsigned const TargetRegisterInfo * TRI
static GCMetadataPrinterRegistry::Add< OcamlGCMetadataPrinter > Y("ocaml", "ocaml 3.10-compatible collector")
PassBuilder PB(Machine, PassOpts->PTO, std::nullopt, &PIC)
static cl::opt< bool > EnableRedundantCopyElimination("riscv-enable-copyelim", cl::desc("Enable the redundant copy elimination pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableMachinePipeliner("riscv-enable-pipeliner", cl::desc("Enable Machine Pipeliner for RISC-V"), cl::init(false), cl::Hidden)
static cl::opt< bool > EnableSinkFold("riscv-enable-sink-fold", cl::desc("Enable sinking and folding of instruction copies"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnablePostMISchedLoadStoreClustering("riscv-postmisched-load-store-clustering", cl::Hidden, cl::desc("Enable PostRA load and store clustering in the machine scheduler"), cl::init(true))
static cl::opt< bool > EnableVLOptimizer("riscv-enable-vl-optimizer", cl::desc("Enable the RISC-V VL Optimizer pass"), cl::init(true), cl::Hidden)
static cl::opt< bool > EnableLoopDataPrefetch("riscv-enable-loop-data-prefetch", cl::Hidden, cl::desc("Enable the loop data prefetch pass"), cl::init(true))
static cl::opt< unsigned > RVVVectorBitsMaxOpt("riscv-v-vector-bits-max", cl::desc("Assume V extension vector registers are at most this big, " "with zero meaning no maximum size is assumed."), cl::init(0), cl::Hidden)
static cl::opt< cl::boolOrDefault > EnableGlobalMerge("riscv-enable-global-merge", cl::Hidden, cl::desc("Enable the global merge pass"))
LLVM_EXTERNAL_VISIBILITY void LLVMInitializeRISCVTarget()
static cl::opt< bool > EnableRISCVCopyPropagation("riscv-enable-copy-propagation", cl::desc("Enable the copy propagation with RISC-V copy instr"), cl::init(true), cl::Hidden)
static cl::opt< int > RVVVectorBitsMinOpt("riscv-v-vector-bits-min", cl::desc("Assume V extension vector registers are at least this big, " "with zero meaning no minimum size is assumed. A value of -1 " "means use Zvl*b extension. This is primarily used to enable " "autovectorization with fixed width vectors."), cl::init(-1), cl::Hidden)
static cl::opt< bool > DisableVectorMaskMutation("riscv-disable-vector-mask-mutation", cl::desc("Disable the vector mask scheduling mutation"), cl::init(false), cl::Hidden)
static Reloc::Model getEffectiveRelocModel(const Triple &TT, std::optional< Reloc::Model > RM)
static cl::opt< bool > EnableRISCVDeadRegisterElimination("riscv-enable-dead-defs", cl::Hidden, cl::desc("Enable the pass that removes dead" " definitons and replaces stores to" " them with stores to x0"), cl::init(true))
static cl::opt< bool > EnableMISchedLoadStoreClustering("riscv-misched-load-store-clustering", cl::Hidden, cl::desc("Enable load and store clustering in the machine scheduler"), cl::init(true))
static cl::opt< bool > EnableMachineCombiner("riscv-enable-machine-combiner", cl::desc("Enable the machine combiner pass"), cl::init(true), cl::Hidden)
This file defines a TargetTransformInfo::Concept conforming object specific to the RISC-V target mach...
Basic Register Allocator
This file describes the interface of the MachineFunctionPass responsible for assigning the generic vi...
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static FunctionPass * useDefaultRegisterAllocator()
-regalloc=... command line option.
Target-Independent Code Generator Pass Configuration Options pass.
This pass exposes codegen information to IR-level passes.
std::optional< unsigned > getVScaleRangeMax() const
Returns the maximum value for the vscale_range attribute or std::nullopt when unknown.
Definition: Attributes.cpp:466
unsigned getVScaleRangeMin() const
Returns the minimum value for the vscale_range attribute.
Definition: Attributes.cpp:460
StringRef getValueAsString() const
Return the attribute's value as a string.
Definition: Attributes.cpp:392
bool isValid() const
Return true if the attribute is any kind of attribute.
Definition: Attributes.h:208
Allocate memory in an ever growing pool, as if by bump-pointer.
Definition: Allocator.h:66
implements a set of functionality in the TargetMachine class for targets that make use of the indepen...
Lightweight error class with error context and mandatory checking.
Definition: Error.h:160
FunctionPass class - This class is used to implement most global optimizations.
Definition: Pass.h:310
This pass is responsible for selecting generic machine instructions to target-specific instructions.
StringRef getABIName() const
getABIName - If this returns a non-empty string this represents the textual name of the ABI that we w...
A single uniqued string.
Definition: Metadata.h:720
Function & getFunction()
Return the LLVM function that this machine code represents.
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
This class provides access to building LLVM's passes.
Definition: PassBuilder.h:105
void registerLateLoopOptimizationsEPCallback(const std::function< void(LoopPassManager &, OptimizationLevel)> &C)
Register a callback for a default optimizer pipeline extension point.
Definition: PassBuilder.h:421
LLVM_ATTRIBUTE_MINSIZE std::enable_if_t< is_detected< HasRunOnLoopT, PassT >::value > addPass(PassT &&Pass)
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
This implementation is used for RISC-V ELF targets.
RISCVMachineFunctionInfo - This class is derived from MachineFunctionInfo and contains private RISCV-...
yaml::MachineFunctionInfo * createDefaultFuncInfoYAML() const override
Allocate and return a default initialized instance of the YAML representation for the MachineFunction...
RISCVTargetMachine(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)
TargetPassConfig * createPassConfig(PassManagerBase &PM) override
Create a pass configuration object to be used by addPassToEmitX methods for generating a pipeline of ...
void registerPassBuilderCallbacks(PassBuilder &PB) override
Allow the target to modify the pass pipeline.
bool isNoopAddrSpaceCast(unsigned SrcAS, unsigned DstAS) const override
Returns true if a cast between SrcAS and DestAS is a noop.
TargetTransformInfo getTargetTransformInfo(const Function &F) const override
Get a TargetTransformInfo implementation for the target.
MachineFunctionInfo * createMachineFunctionInfo(BumpPtrAllocator &Allocator, const Function &F, const TargetSubtargetInfo *STI) const override
Create the target's instance of MachineFunctionInfo.
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.
const RISCVSubtarget * getSubtargetImpl() const =delete
This pass implements the reg bank selector pass used in the GlobalISel pipeline.
Definition: RegBankSelect.h:91
RegisterPassParser class - Handle the addition of new machine passes.
RegisterRegAllocBase class - Track the registration of register allocators.
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
Instances of this class encapsulate one diagnostic report, allowing printing to a raw_ostream as a ca...
Definition: SourceMgr.h:281
Represents a range in source code.
Definition: SMLoc.h:48
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...
void addMutation(std::unique_ptr< ScheduleDAGMutation > Mutation)
Add a postprocessing step to the DAG builder.
const TargetInstrInfo * TII
Target instruction information.
Definition: ScheduleDAG.h:575
const TargetRegisterInfo * TRI
Target processor register info.
Definition: ScheduleDAG.h:576
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:51
std::string str() const
str - Get the contents as an std::string.
Definition: StringRef.h:229
Triple TargetTriple
Triple string, CPU name, and target feature strings the TargetMachine instance is created with.
Definition: TargetMachine.h:96
void setMachineOutliner(bool Enable)
void setCFIFixup(bool Enable)
void setSupportsDefaultOutlining(bool Enable)
std::string TargetFS
Definition: TargetMachine.h:98
std::string TargetCPU
Definition: TargetMachine.h:97
std::unique_ptr< const MCSubtargetInfo > STI
TargetOptions Options
void resetTargetOptions(const Function &F) const
Reset the target options based on the function's attributes.
MCTargetOptions MCOptions
Machine level options.
Target-Independent Code Generator Pass Configuration Options.
virtual void addCodeGenPrepare()
Add pass to prepare the LLVM IR for code generation.
virtual bool addRegAssignAndRewriteFast()
Add core register allocator passes which do the actual register assignment and rewriting.
virtual void addIRPasses()
Add common target configurable passes that perform LLVM IR to IR transforms following machine indepen...
virtual void addFastRegAlloc()
addFastRegAlloc - Add the minimum set of target-independent passes that are required for fast registe...
virtual void addMachineSSAOptimization()
addMachineSSAOptimization - Add standard passes that optimize machine instructions in SSA form.
virtual bool addRegAssignAndRewriteOptimized()
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
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:44
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.
Definition: raw_ostream.h:691
Interfaces for registering analysis passes, producing common pass manager configurations,...
@ C
The default llvm calling convention, compatible with C.
Definition: CallingConv.h:34
ABI getTargetABI(StringRef ABIName)
static constexpr unsigned RVVBitsPerBlock
initializer< Ty > init(const Ty &Val)
Definition: CommandLine.h:443
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
FunctionPass * createRISCVLandingPadSetupPass()
FunctionPass * createFastRegisterAllocator()
FastRegisterAllocation Pass - This pass register allocates as fast as possible.
FunctionPass * createRISCVPostLegalizerCombiner()
void initializeRISCVPushPopOptPass(PassRegistry &)
void initializeRISCVExpandPseudoPass(PassRegistry &)
FunctionPass * createRISCVMoveMergePass()
createRISCVMoveMergePass - returns an instance of the move merge pass.
char & InitUndefID
Definition: InitUndef.cpp:98
FunctionPass * createTypePromotionLegacyPass()
Create IR Type Promotion pass.
void initializeRISCVDeadRegisterDefinitionsPass(PassRegistry &)
FunctionPass * createGreedyRegisterAllocator()
Greedy register allocation pass - This pass implements a global register allocator for optimized buil...
void initializeRISCVPreLegalizerCombinerPass(PassRegistry &)
FunctionPass * createRISCVExpandAtomicPseudoPass()
FunctionPass * createRISCVPostRAExpandPseudoPass()
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 * createRISCVInsertReadWriteCSRPass()
Target & getTheRISCV32Target()
void initializeRISCVInsertVSETVLIPass(PassRegistry &)
FunctionPass * createRISCVVLOptimizerPass()
char & PostRASchedulerID
PostRAScheduler - This pass performs post register allocation scheduling.
std::unique_ptr< CSEConfigBase > getStandardCSEConfigForOpt(CodeGenOptLevel Level)
Definition: CSEInfo.cpp:79
FunctionPass * createRISCVDeadRegisterDefinitionsPass()
char & PostMachineSchedulerID
PostMachineScheduler - This pass schedules machine instructions postRA.
ScheduleDAGMILive * createGenericSchedLive(MachineSchedContext *C)
Create the standard converging machine scheduler.
FunctionPass * createRISCVGatherScatterLoweringPass()
FunctionPass * createRISCVMergeBaseOffsetOptPass()
Returns an instance of the Merge Base Offset Optimization pass.
char & MachineCombinerID
This pass performs instruction combining using trace metrics to estimate critical-path and resource d...
void initializeRISCVPostRAExpandPseudoPass(PassRegistry &)
CodeModel::Model getEffectiveCodeModel(std::optional< CodeModel::Model > CM, CodeModel::Model Default)
Helper method for getting the code model, returning Default if CM does not have a value.
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
Definition: MathExtras.h:291
FunctionPass * createRISCVPreLegalizerCombiner()
char & BranchRelaxationPassID
BranchRelaxation - This pass replaces branches that need to jump further than is supported by a branc...
FunctionPass * createRISCVO0PreLegalizerCombiner()
void initializeRISCVDAGToDAGISelLegacyPass(PassRegistry &)
FunctionPass * createRISCVPushPopOptimizationPass()
createRISCVPushPopOptimizationPass - returns an instance of the Push/Pop optimization pass.
FunctionPass * createRISCVMakeCompressibleOptPass()
Returns an instance of the Make Compressible Optimization pass.
FunctionPass * createRISCVRedundantCopyEliminationPass()
FunctionPass * createKCFIPass()
Lowers KCFI operand bundles for indirect calls.
Definition: KCFI.cpp:61
void initializeRISCVInsertWriteVXRMPass(PassRegistry &)
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...
FunctionPass * createLoopDataPrefetchPass()
void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
Definition: Error.cpp:167
void initializeRISCVInsertReadWriteCSRPass(PassRegistry &)
FunctionPass * createRISCVInsertVSETVLIPass()
Returns an instance of the Insert VSETVLI pass.
CodeGenOptLevel
Code generation optimization level.
Definition: CodeGen.h:54
FunctionPass * createRISCVIndirectBranchTrackingPass()
FunctionPass * createRISCVOptWInstrsPass()
FunctionPass * createInterleavedAccessPass()
InterleavedAccess Pass - This pass identifies and matches interleaved memory accesses to target speci...
std::unique_ptr< ScheduleDAGMutation > createRISCVVectorMaskDAGMutation(const TargetRegisterInfo *TRI)
FunctionPass * createBasicRegisterAllocator()
BasicRegisterAllocation Pass - This pass implements a degenerate global register allocator using the ...
void initializeGlobalISel(PassRegistry &)
Initialize all passes linked into the GlobalISel library.
Definition: GlobalISel.cpp:17
ScheduleDAGMI * createGenericSchedPostRA(MachineSchedContext *C)
Create a generic scheduler with no vreg liveness or DAG mutation passes.
void initializeRISCVMakeCompressibleOptPass(PassRegistry &)
FunctionPass * createRISCVCodeGenPreparePass()
char & MachinePipelinerID
This pass performs software pipelining on machine instructions.
ModulePass * createBarrierNoopPass()
createBarrierNoopPass - This pass is purely a module pass barrier in a pass manager.
void initializeRISCVVLOptimizerPass(PassRegistry &)
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 initializeRISCVOptWInstrsPass(PassRegistry &)
FunctionPass * createUnpackMachineBundles(std::function< bool(const MachineFunction &)> Ftor)
void initializeRISCVCodeGenPreparePass(PassRegistry &)
Target & getTheRISCV64Target()
FunctionPass * createRISCVVectorPeepholePass()
void call_once(once_flag &flag, Function &&F, Args &&... ArgList)
Execute the function specified as a parameter once.
Definition: Threading.h:87
void initializeRISCVO0PreLegalizerCombinerPass(PassRegistry &)
void initializeKCFIPass(PassRegistry &)
void initializeRISCVMergeBaseOffsetOptPass(PassRegistry &)
FunctionPass * createRISCVISelDag(RISCVTargetMachine &TM, CodeGenOptLevel OptLevel)
FunctionPass * createVirtRegRewriter(bool ClearVirtRegs=true)
Definition: VirtRegMap.cpp:734
void initializeRISCVGatherScatterLoweringPass(PassRegistry &)
FunctionPass * createRISCVExpandPseudoPass()
FunctionPass * createRISCVPreRAExpandPseudoPass()
FunctionPass * createAtomicExpandLegacyPass()
AtomicExpandPass - At IR level this pass replace atomic instructions with __atomic_* library calls,...
T bit_floor(T Value)
Returns the largest integral power of two no greater than Value if Value is nonzero.
Definition: bit.h:327
FunctionPass * createRISCVInsertWriteVXRMPass()
MachineFunctionPass * createMachineCopyPropagationPass(bool UseCopyInstr)
void initializeRISCVVectorPeepholePass(PassRegistry &)
FunctionPass * createRISCVZacasABIFixPass()
void initializeRISCVPreRAExpandPseudoPass(PassRegistry &)
void initializeRISCVPostLegalizerCombinerPass(PassRegistry &)
void initializeRISCVMoveMergePass(PassRegistry &)
Implement std::hash so that hash_code can be used in STL containers.
Definition: BitVector.h:858
#define N
MachineFunctionInfo - This class can be derived from and used by targets to hold private target-speci...
MachineSchedContext provides enough context from the MachineScheduler pass for the target to instanti...
static bool isRVVRegClass(const TargetRegisterClass *RC)
RegisterTargetMachine - Helper template for registering a target machine implementation,...
The llvm::once_flag structure.
Definition: Threading.h:68
Targets should override this in a way that mirrors the implementation of llvm::MachineFunctionInfo.