AVRTargetMachine.cpp revision 360784
1//===-- AVRTargetMachine.cpp - Define TargetMachine for AVR ---------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines the AVR specific subclass of TargetMachine.
10//
11//===----------------------------------------------------------------------===//
12
13#include "AVRTargetMachine.h"
14
15#include "llvm/CodeGen/Passes.h"
16#include "llvm/CodeGen/TargetPassConfig.h"
17#include "llvm/IR/LegacyPassManager.h"
18#include "llvm/IR/Module.h"
19#include "llvm/Support/TargetRegistry.h"
20
21#include "AVR.h"
22#include "AVRTargetObjectFile.h"
23#include "MCTargetDesc/AVRMCTargetDesc.h"
24#include "TargetInfo/AVRTargetInfo.h"
25
26namespace llvm {
27
28static const char *AVRDataLayout = "e-P1-p:16:8-i8:8-i16:8-i32:8-i64:8-f32:8-f64:8-n8-a:8";
29
30/// Processes a CPU name.
31static StringRef getCPU(StringRef CPU) {
32  if (CPU.empty() || CPU == "generic") {
33    return "avr2";
34  }
35
36  return CPU;
37}
38
39static Reloc::Model getEffectiveRelocModel(Optional<Reloc::Model> RM) {
40  return RM.hasValue() ? *RM : Reloc::Static;
41}
42
43AVRTargetMachine::AVRTargetMachine(const Target &T, const Triple &TT,
44                                   StringRef CPU, StringRef FS,
45                                   const TargetOptions &Options,
46                                   Optional<Reloc::Model> RM,
47                                   Optional<CodeModel::Model> CM,
48                                   CodeGenOpt::Level OL, bool JIT)
49    : LLVMTargetMachine(T, AVRDataLayout, TT, getCPU(CPU), FS, Options,
50                        getEffectiveRelocModel(RM),
51                        getEffectiveCodeModel(CM, CodeModel::Small), OL),
52      SubTarget(TT, getCPU(CPU), FS, *this) {
53  this->TLOF = std::make_unique<AVRTargetObjectFile>();
54  initAsmInfo();
55}
56
57namespace {
58/// AVR Code Generator Pass Configuration Options.
59class AVRPassConfig : public TargetPassConfig {
60public:
61  AVRPassConfig(AVRTargetMachine &TM, PassManagerBase &PM)
62      : TargetPassConfig(TM, PM) {}
63
64  AVRTargetMachine &getAVRTargetMachine() const {
65    return getTM<AVRTargetMachine>();
66  }
67
68  bool addInstSelector() override;
69  void addPreSched2() override;
70  void addPreEmitPass() override;
71  void addPreRegAlloc() override;
72};
73} // namespace
74
75TargetPassConfig *AVRTargetMachine::createPassConfig(PassManagerBase &PM) {
76  return new AVRPassConfig(*this, PM);
77}
78
79extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeAVRTarget() {
80  // Register the target.
81  RegisterTargetMachine<AVRTargetMachine> X(getTheAVRTarget());
82
83  auto &PR = *PassRegistry::getPassRegistry();
84  initializeAVRExpandPseudoPass(PR);
85  initializeAVRRelaxMemPass(PR);
86}
87
88const AVRSubtarget *AVRTargetMachine::getSubtargetImpl() const {
89  return &SubTarget;
90}
91
92const AVRSubtarget *AVRTargetMachine::getSubtargetImpl(const Function &) const {
93  return &SubTarget;
94}
95
96//===----------------------------------------------------------------------===//
97// Pass Pipeline Configuration
98//===----------------------------------------------------------------------===//
99
100bool AVRPassConfig::addInstSelector() {
101  // Install an instruction selector.
102  addPass(createAVRISelDag(getAVRTargetMachine(), getOptLevel()));
103  // Create the frame analyzer pass used by the PEI pass.
104  addPass(createAVRFrameAnalyzerPass());
105
106  return false;
107}
108
109void AVRPassConfig::addPreRegAlloc() {
110  // Create the dynalloc SP save/restore pass to handle variable sized allocas.
111  addPass(createAVRDynAllocaSRPass());
112}
113
114void AVRPassConfig::addPreSched2() {
115  addPass(createAVRRelaxMemPass());
116  addPass(createAVRExpandPseudoPass());
117}
118
119void AVRPassConfig::addPreEmitPass() {
120  // Must run branch selection immediately preceding the asm printer.
121  addPass(&BranchRelaxationPassID);
122}
123
124} // end of namespace llvm
125