LLVM: lib/Target/PowerPC/PPCTargetMachine.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

46#include

47#include

48#include

49#include

50

51using namespace llvm;

52

53

56 cl::desc("enable coalescing of duplicate branches for PPC"));

57static cl::

59 cl::desc("Disable CTR loops for PPC"));

60

61static cl::

63 cl::desc("Disable PPC loop instr form prep"));

64

68

69static cl::

71 cl::desc("Disable VSX Swap Removal for PPC"));

72

73static cl::

75 cl::desc("Disable machine peepholes for PPC"));

76

79 cl::desc("Enable optimizations on complex GEPs"),

81

84 cl::desc("enable software prefetching on PPC"),

86

89 cl::desc("Add extra TOC register dependencies"),

91

94 cl::desc("Enable the machine combiner pass"),

96

99 cl::desc("Expand eligible cr-logical binary ops to branches"),

101

103 "enable-ppc-gen-scalar-mass", cl::init(false),

104 cl::desc("Enable lowering math functions to their corresponding MASS "

105 "(scalar) entries"),

107

110 cl::desc("Enable the global merge pass"));

111

115 cl::desc("Maximum global merge offset"));

116

118

123

125#ifndef NDEBUG

127#endif

147}

148

151}

152

153

156 std::string Ret;

157

158

160 Ret = "e";

161 else

162 Ret = "E";

163

165

166

167

169 Ret += "-p:32:32";

170

171

172

173

174 if ((T.getArch() == Triple::ppc64 && T.isPPC64ELFv2ABI())) {

175 Ret += "-Fi64";

176 } else if (T.isOSAIX()) {

177 Ret += is64Bit ? "-Fi64" : "-Fi32";

178 } else {

179 Ret += "-Fn32";

180 }

181

182

183

184 Ret += "-i64:64";

185

186

188 Ret += "-i128:128-n32:64";

189 else

190 Ret += "-n32";

191

192

193

194

195 if (is64Bit && (T.isOSAIX() || T.isOSLinux()))

196 Ret += "-S128-v256:256:256-v512:512:512";

197

198 return Ret;

199}

200

203 std::string FullFS = std::string(FS);

204

205

207 if (!FullFS.empty())

208 FullFS = "+64bit," + FullFS;

209 else

210 FullFS = "+64bit";

211 }

212

213 if (OL >= CodeGenOptLevel::Default) {

214 if (!FullFS.empty())

215 FullFS = "+crbits," + FullFS;

216 else

217 FullFS = "+crbits";

218 }

219

220 if (OL != CodeGenOptLevel::None) {

221 if (!FullFS.empty())

222 FullFS = "+invariant-function-descriptors," + FullFS;

223 else

224 FullFS = "+invariant-function-descriptors";

225 }

226

227 if (TT.isOSAIX()) {

228 if (!FullFS.empty())

229 FullFS = "+aix," + FullFS;

230 else

231 FullFS = "+aix";

232 }

233

234 return FullFS;

235}

236

237static std::unique_ptr createTLOF(const Triple &TT) {

238 if (TT.isOSAIX())

239 return std::make_unique();

240

241 return std::make_unique();

242}

243

246 if (Options.MCOptions.getABIName().starts_with("elfv1"))

248 else if (Options.MCOptions.getABIName().starts_with("elfv2"))

250

252 "Unknown target-abi option!");

253

254 switch (TT.getArch()) {

258 if (TT.isPPC64ELFv2ABI())

260 else

262 default:

264 }

265}

266

268 std::optionalReloc::Model RM) {

269 if (TT.isOSAIX() && RM && *RM != Reloc::PIC_)

270 report_fatal_error("invalid relocation model, AIX only supports PIC",

271 false);

272

273 if (RM)

274 return *RM;

275

276

277 if (TT.getArch() == Triple::ppc64 || TT.isOSAIX())

279

280

282}

283

286 bool JIT) {

287 if (CM) {

289 report_fatal_error("Target does not support the tiny CodeModel", false);

291 report_fatal_error("Target does not support the kernel CodeModel", false);

292 return *CM;

293 }

294

295 if (JIT)

297 if (TT.isOSAIX())

299

300 assert(TT.isOSBinFormatELF() && "All remaining PPC OSes are ELF based.");

301

302 if (TT.isArch32Bit())

304

305 assert(TT.isArch64Bit() && "Unsupported PPC architecture.");

307}

308

309

314 std::make_unique(C) :

315 std::make_unique(C));

316

318 if (ST.hasStoreFusion())

320 if (ST.hasFusion())

322

323 return DAG;

324}

325

330 new ScheduleDAGMI(C, ST.usePPCPostRASchedStrategy() ?

331 std::make_unique(C) :

332 std::make_unique(C), true);

333

334 if (ST.hasStoreFusion())

336 if (ST.hasFusion())

338 return DAG;

339}

340

341

342

343

344

348 std::optionalReloc::Model RM,

349 std::optionalCodeModel::Model CM,

359}

360

362

365 Attribute CPUAttr = F.getFnAttribute("target-cpu");

366 Attribute TuneAttr = F.getFnAttribute("tune-cpu");

367 Attribute FSAttr = F.getFnAttribute("target-features");

368

369 std::string CPU =

371 std::string TuneCPU =

373 std::string FS =

375

376

377

378

379

380

381 bool SoftFloat = F.getFnAttribute("use-soft-float").getValueAsBool();

382

383

384 if (SoftFloat)

385 FS += FS.empty() ? "-hard-float" : ",-hard-float";

386

387 auto &I = SubtargetMap[CPU + TuneCPU + FS];

388 if (I) {

389

390

391

393 I = std::make_unique(

395

396

397

398

399

400

402 }

403 return I.get();

404}

405

406

407

408

409

410namespace {

411

412

414public:

417

418

419 if (TM.getOptLevel() != CodeGenOptLevel::None)

421 }

422

424 return getTM();

425 }

426

427 void addIRPasses() override;

428 bool addPreISel() override;

429 bool addILPOpts() override;

430 bool addInstSelector() override;

431 void addMachineSSAOptimization() override;

432 void addPreRegAlloc() override;

433 void addPreSched2() override;

434 void addPreEmitPass() override;

435 void addPreEmitPass2() override;

436

437 bool addIRTranslator() override;

438 bool addLegalizeMachineIR() override;

439 bool addRegBankSelect() override;

440 bool addGlobalInstructionSelect() override;

441

445 }

449 }

450};

451

452}

453

455 return new PPCPassConfig(*this, PM);

456}

457

458void PPCPassConfig::addIRPasses() {

462

463

465

466

467

472 }

473

474

477

479

480

481

483

484

486

487

489 }

490

492}

493

494bool PPCPassConfig::addPreISel() {

495

496

501 true));

502

505

508

509 return false;

510}

511

512bool PPCPassConfig::addILPOpts() {

514

517

518 return true;

519}

520

521bool PPCPassConfig::addInstSelector() {

522

523 addPass(createPPCISelDag(getPPCTargetMachine(), getOptLevel()));

524

525#ifndef NDEBUG

528#endif

529

531 return false;

532}

533

534void PPCPassConfig::addMachineSSAOptimization() {

535

536

539

540

541

545

546

550

553

554

558 }

559}

560

561void PPCPassConfig::addPreRegAlloc() {

566 }

567

568

569 if (getPPCTargetMachine().isPositionIndependent()) {

570

571

572

573

576 }

579

582}

583

584void PPCPassConfig::addPreSched2() {

587}

588

589void PPCPassConfig::addPreEmitPass() {

591

594}

595

596void PPCPassConfig::addPreEmitPass2() {

597

598

599

601

603}

604

608}

609

612 "Unable to determine endianness");

614}

615

619 return PPCFunctionInfo::create(Allocator, F, STI);

620}

621

624 "Run PowerPC PreRA specific scheduler",

626

629 "Run PowerPC PostRA specific scheduler",

631

632

633bool PPCPassConfig::addIRTranslator() {

635 return false;

636}

637

638bool PPCPassConfig::addLegalizeMachineIR() {

640 return false;

641}

642

643bool PPCPassConfig::addRegBankSelect() {

645 return false;

646}

647

648bool PPCPassConfig::addGlobalInstructionSelect() {

650 return false;

651}

static cl::opt< bool > EnableGEPOpt("aarch64-enable-gep-opt", cl::Hidden, cl::desc("Enable optimizations on complex GEPs"), cl::init(false))

This file contains the simple types necessary to represent the attributes associated with functions a...

static cl::opt< bool > DisableMIPeephole("disable-bpf-peephole", cl::Hidden, cl::desc("Disable machine peepholes for BPF"))

static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")

static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")

static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")

#define LLVM_EXTERNAL_VISIBILITY

static cl::opt< unsigned > GlobalMergeMaxOffset("global-merge-max-offset", cl::Hidden, cl::desc("Set maximum offset for global merge pass"), cl::init(0))

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 cl::opt< bool > VSXFMAMutateEarly("schedule-ppc-vsx-fma-mutation-early", cl::Hidden, cl::desc("Schedule VSX FMA instruction mutation early"))

static cl::opt< bool > EnableMachineCombinerPass("ppc-machine-combiner", cl::desc("Enable the machine combiner pass"), cl::init(true), cl::Hidden)

static bool isLittleEndianTriple(const Triple &T)

static MachineSchedRegistry PPCPostRASchedRegistry("ppc-postra", "Run PowerPC PostRA specific scheduler", createPPCPostMachineScheduler)

static cl::opt< bool > DisableCTRLoops("disable-ppc-ctrloops", cl::Hidden, cl::desc("Disable CTR loops for PPC"))

static cl::opt< bool > DisableMIPeephole("disable-ppc-peephole", cl::Hidden, cl::desc("Disable machine peepholes for PPC"))

static cl::opt< bool > EnableExtraTOCRegDeps("enable-ppc-extra-toc-reg-deps", cl::desc("Add extra TOC register dependencies"), cl::init(true), cl::Hidden)

static PPCTargetMachine::PPCABI computeTargetABI(const Triple &TT, const TargetOptions &Options)

static cl::opt< bool > EnablePrefetch("enable-ppc-prefetching", cl::desc("enable software prefetching on PPC"), cl::init(false), cl::Hidden)

static cl::opt< bool > EnablePPCGenScalarMASSEntries("enable-ppc-gen-scalar-mass", cl::init(false), cl::desc("Enable lowering math functions to their corresponding MASS " "(scalar) entries"), cl::Hidden)

static cl::opt< bool > ReduceCRLogical("ppc-reduce-cr-logicals", cl::desc("Expand eligible cr-logical binary ops to branches"), cl::init(true), cl::Hidden)

static cl::opt< bool > EnableGEPOpt("ppc-gep-opt", cl::Hidden, cl::desc("Enable optimizations on complex GEPs"), cl::init(true))

static ScheduleDAGInstrs * createPPCPostMachineScheduler(MachineSchedContext *C)

static CodeModel::Model getEffectivePPCCodeModel(const Triple &TT, std::optional< CodeModel::Model > CM, bool JIT)

static std::string getDataLayoutString(const Triple &T)

Return the datalayout string of a subtarget.

static cl::opt< bool > DisableInstrFormPrep("disable-ppc-instr-form-prep", cl::Hidden, cl::desc("Disable PPC loop instr form prep"))

static std::string computeFSAdditions(StringRef FS, CodeGenOptLevel OL, const Triple &TT)

static MachineSchedRegistry PPCPreRASchedRegistry("ppc-prera", "Run PowerPC PreRA specific scheduler", createPPCMachineScheduler)

static cl::opt< unsigned > GlobalMergeMaxOffset("ppc-global-merge-max-offset", cl::Hidden, cl::init(0x7fff), cl::desc("Maximum global merge offset"))

static cl::opt< bool > DisableVSXSwapRemoval("disable-ppc-vsx-swap-removal", cl::Hidden, cl::desc("Disable VSX Swap Removal for PPC"))

static Reloc::Model getEffectiveRelocModel(const Triple &TT, std::optional< Reloc::Model > RM)

static cl::opt< bool > EnableBranchCoalescing("enable-ppc-branch-coalesce", cl::Hidden, cl::desc("enable coalescing of duplicate branches for PPC"))

static ScheduleDAGInstrs * createPPCMachineScheduler(MachineSchedContext *C)

static cl::opt< bool > EnableGlobalMerge("ppc-global-merge", cl::Hidden, cl::init(false), cl::desc("Enable the global merge pass"))

LLVM_EXTERNAL_VISIBILITY void LLVMInitializePowerPCTarget()

This file a TargetTransformInfo::Concept conforming object specific to the PPC target machine.

This file describes the interface of the MachineFunctionPass responsible for assigning the generic vi...

assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())

Target-Independent Code Generator Pass Configuration Options pass.

This pass exposes codegen information to IR-level passes.

static std::unique_ptr< TargetLoweringObjectFile > createTLOF()

static bool is64Bit(const char *name)

StringRef getValueAsString() const

Return the attribute's value as a string.

bool isValid() const

Return true if the attribute is any kind of attribute.

Allocate memory in an ever growing pool, as if by bump-pointer.

implements a set of functionality in the TargetMachine class for targets that make use of the indepen...

static const char * getManglingComponent(const Triple &T)

This pass is responsible for selecting generic machine instructions to target-specific instructions.

MachineSchedRegistry provides a selection of available machine instruction schedulers.

Common code between 32-bit and 64-bit PowerPC targets.

const PPCSubtarget * getSubtargetImpl() const =delete

~PPCTargetMachine() override

bool isLittleEndian() const

PPCTargetMachine(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)

TargetTransformInfo getTargetTransformInfo(const Function &F) const override

Get a TargetTransformInfo implementation for the target.

TargetPassConfig * createPassConfig(PassManagerBase &PM) override

Create a pass configuration object to be used by addPassToEmitX methods for generating a pipeline of ...

MachineFunctionInfo * createMachineFunctionInfo(BumpPtrAllocator &Allocator, const Function &F, const TargetSubtargetInfo *STI) const override

Create the target's instance of MachineFunctionInfo.

PassRegistry - This class manages the registration and intitialization of the pass subsystem as appli...

static 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.

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...

StringRef - Represent a constant reference to a string, i.e.

std::string str() const

str - Get the contents as an std::string.

CodeGenOptLevel getOptLevel() const

Returns the optimization level: None, Less, Default, or Aggressive.

Triple TargetTriple

Triple string, CPU name, and target feature strings the TargetMachine instance is created with.

const Triple & getTargetTriple() const

std::unique_ptr< const MCSubtargetInfo > STI

void resetTargetOptions(const Function &F) const

Reset the target options based on the function's attributes.

Target-Independent Code Generator Pass Configuration Options.

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.

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.

int getNumOccurrences() const

PassManagerBase - An abstract interface to allow code to add passes to a pass manager without having ...

@ C

The default llvm calling convention, compatible with C.

initializer< Ty > init(const Ty &Val)

This is an optimization pass for GlobalISel generic memory operations.

FunctionPass * createPPCPreEmitPeepholePass()

Target & getThePPC64LETarget()

void initializePPCTLSDynamicCallPass(PassRegistry &)

char & RegisterCoalescerID

RegisterCoalescer - This pass merges live ranges to eliminate copies.

FunctionPass * createPPCLoopInstrFormPrepPass(PPCTargetMachine &TM)

void initializePPCVSXFMAMutatePass(PassRegistry &)

void initializePPCLowerMASSVEntriesPass(PassRegistry &)

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...

char & PostRASchedulerID

PostRAScheduler - This pass performs post register allocation scheduling.

Target & getThePPC32Target()

FunctionPass * createPPCCTRLoopsPass()

char & MachineSchedulerID

MachineScheduler - This pass schedules machine instructions.

FunctionPass * createPPCTLSDynamicCallPass()

char & PostMachineSchedulerID

PostMachineScheduler - This pass schedules machine instructions postRA.

FunctionPass * createPPCEarlyReturnPass()

void initializePPCPreEmitPeepholePass(PassRegistry &)

char & EarlyIfConverterLegacyID

EarlyIfConverter - This pass performs if-conversion on SSA form by inserting cmov instructions.

FunctionPass * createPPCExpandAtomicPseudoPass()

void initializePPCTOCRegDepsPass(PassRegistry &)

void initializePPCReduceCRLogicalsPass(PassRegistry &)

char & MachineCombinerID

This pass performs instruction combining using trace metrics to estimate critical-path and resource d...

void initializePPCVSXCopyPass(PassRegistry &)

FunctionPass * createPPCVSXCopyPass()

void initializePPCCTRLoopsVerifyPass(PassRegistry &)

FunctionPass * createPPCVSXSwapRemovalPass()

void initializePPCCTRLoopsPass(PassRegistry &)

ModulePass * createPPCLowerMASSVEntriesPass()

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.

void initializePPCDAGToDAGISelLegacyPass(PassRegistry &)

ModulePass * createPPCGenScalarMASSEntriesPass()

void initializePPCEarlyReturnPass(PassRegistry &)

CodeGenOptLevel

Code generation optimization level.

void initializePPCGenScalarMASSEntriesPass(PassRegistry &)

FunctionPass * createPPCReduceCRLogicalsPass()

FunctionPass * createPPCISelDag(PPCTargetMachine &TM, CodeGenOptLevel OL)

createPPCISelDag - This pass converts a legalized DAG into a PowerPC-specific DAG,...

void initializePPCExpandAtomicPseudoPass(PassRegistry &)

FunctionPass * createSeparateConstOffsetFromGEPPass(bool LowerGEP=false)

FunctionPass * createPPCBranchCoalescingPass()

createPPCBranchCoalescingPass - returns an instance of the Branch Coalescing Pass

Target & getThePPC64Target()

void initializeGlobalISel(PassRegistry &)

Initialize all passes linked into the GlobalISel library.

void initializePPCBSelPass(PassRegistry &)

char & MachinePipelinerID

This pass performs software pipelining on machine instructions.

FunctionPass * createPPCTOCRegDepsPass()

FunctionPass * createPPCCTRLoopsVerify()

void initializePPCBranchCoalescingPass(PassRegistry &)

void initializePPCBoolRetToIntPass(PassRegistry &)

void initializePPCMIPeepholePass(PassRegistry &)

std::unique_ptr< ScheduleDAGMutation > createPowerPCMacroFusionDAGMutation()

Note that you have to add: DAG.addMutation(createPowerPCMacroFusionDAGMutation()); to PPCPassConfig::...

void initializePPCVSXSwapRemovalPass(PassRegistry &)

char & LiveVariablesID

LiveVariables pass - This pass computes the set of blocks in which each variable is life and sets mac...

Target & getThePPC32LETarget()

char & IfConverterID

IfConverter - This pass performs machine code if conversion.

void initializePPCLoopInstrFormPrepPass(PassRegistry &)

FunctionPass * createAtomicExpandLegacyPass()

AtomicExpandPass - At IR level this pass replace atomic instructions with __atomic_* library calls,...

FunctionPass * createEarlyCSEPass(bool UseMemorySSA=false)

std::unique_ptr< ScheduleDAGMutation > createCopyConstrainDAGMutation(const TargetInstrInfo *TII, const TargetRegisterInfo *TRI)

FunctionPass * createPPCBranchSelectionPass()

FunctionPass * createPPCBoolRetToIntPass()

char & DeadMachineInstructionElimID

DeadMachineInstructionElim - This pass removes dead machine instructions.

FunctionPass * createHardwareLoopsLegacyPass()

Create Hardware Loop pass.

FunctionPass * createPPCMIPeepholePass()

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...

RegisterTargetMachine - Helper template for registering a target machine implementation,...