11849Swollman//===-- llvm/Target/TargetLoweringObjectFile.h - Object Info ----*- C++ -*-===//
21849Swollman//
31849Swollman// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
41849Swollman// See https://llvm.org/LICENSE.txt for license information.
51849Swollman// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
61849Swollman//
71849Swollman//===----------------------------------------------------------------------===//
81849Swollman//
91849Swollman// This file implements classes used to handle lowerings specific to common
101849Swollman// object file formats.
111849Swollman//
121849Swollman//===----------------------------------------------------------------------===//
131849Swollman
141849Swollman#ifndef LLVM_TARGET_TARGETLOWERINGOBJECTFILE_H
151849Swollman#define LLVM_TARGET_TARGETLOWERINGOBJECTFILE_H
161849Swollman
1797748Sschweikh#include "llvm/MC/MCObjectFileInfo.h"
181849Swollman#include "llvm/MC/MCRegister.h"
191849Swollman#include <cstdint>
201849Swollman
211849Swollmannamespace llvm {
221849Swollman
231849Swollmanstruct Align;
241849Swollmanclass Constant;
251849Swollmanclass DataLayout;
261849Swollmanclass Function;
271849Swollmanclass GlobalObject;
281849Swollmanclass GlobalValue;
291849Swollmanclass MachineBasicBlock;
301849Swollmanclass MachineModuleInfo;
3185437Speterclass Mangler;
3293000Sobrienclass MCContext;
331849Swollmanclass MCExpr;
341849Swollmanclass MCSection;
351849Swollmanclass MCSymbol;
361849Swollmanclass MCSymbolRefExpr;
371849Swollmanclass MCStreamer;
381849Swollmanclass MCValue;
391849Swollmanclass Module;
401849Swollmanclass SectionKind;
411849Swollmanclass StringRef;
421849Swollmanclass TargetMachine;
431849Swollmanclass DSOLocalEquivalent;
441849Swollman
451849Swollmanclass TargetLoweringObjectFile : public MCObjectFileInfo {
461849Swollman  /// Name-mangler for global names.
471849Swollman  Mangler *Mang = nullptr;
481849Swollman
491849Swollmanprotected:
501849Swollman  bool SupportIndirectSymViaGOTPCRel = false;
511849Swollman  bool SupportGOTPCRelWithOffset = true;
521849Swollman  bool SupportDebugThreadLocalLocation = true;
531849Swollman  bool SupportDSOLocalEquivalentLowering = false;
541849Swollman
551849Swollman  /// PersonalityEncoding, LSDAEncoding, TTypeEncoding - Some encoding values
561849Swollman  /// for EH.
571849Swollman  unsigned PersonalityEncoding = 0;
581849Swollman  unsigned LSDAEncoding = 0;
591849Swollman  unsigned TTypeEncoding = 0;
601849Swollman  unsigned CallSiteEncoding = 0;
611849Swollman
621849Swollman  /// This section contains the static constructor pointer list.
631849Swollman  MCSection *StaticCtorSection = nullptr;
641849Swollman
65184548Speter  /// This section contains the static destructor pointer list.
66217106Skib  MCSection *StaticDtorSection = nullptr;
67217106Skib
68  const TargetMachine *TM = nullptr;
69
70public:
71  TargetLoweringObjectFile() = default;
72  TargetLoweringObjectFile(const TargetLoweringObjectFile &) = delete;
73  TargetLoweringObjectFile &
74  operator=(const TargetLoweringObjectFile &) = delete;
75  virtual ~TargetLoweringObjectFile();
76
77  Mangler &getMangler() const { return *Mang; }
78
79  /// This method must be called before any actual lowering is done.  This
80  /// specifies the current context for codegen, and gives the lowering
81  /// implementations a chance to set up their default sections.
82  virtual void Initialize(MCContext &ctx, const TargetMachine &TM);
83
84  virtual void emitPersonalityValue(MCStreamer &Streamer, const DataLayout &TM,
85                                    const MCSymbol *Sym) const;
86
87  /// Emit the module-level metadata that the platform cares about.
88  virtual void emitModuleMetadata(MCStreamer &Streamer, Module &M) const {}
89
90  /// Emit Call Graph Profile metadata.
91  void emitCGProfileMetadata(MCStreamer &Streamer, Module &M) const;
92
93  /// Get the module-level metadata that the platform cares about.
94  virtual void getModuleMetadata(Module &M) {}
95
96  /// Given a constant with the SectionKind, return a section that it should be
97  /// placed in.
98  virtual MCSection *getSectionForConstant(const DataLayout &DL,
99                                           SectionKind Kind, const Constant *C,
100                                           Align &Alignment) const;
101
102  virtual MCSection *
103  getSectionForMachineBasicBlock(const Function &F,
104                                 const MachineBasicBlock &MBB,
105                                 const TargetMachine &TM) const;
106
107  virtual MCSection *
108  getUniqueSectionForFunction(const Function &F,
109                              const TargetMachine &TM) const;
110
111  /// Classify the specified global variable into a set of target independent
112  /// categories embodied in SectionKind.
113  static SectionKind getKindForGlobal(const GlobalObject *GO,
114                                      const TargetMachine &TM);
115
116  /// This method computes the appropriate section to emit the specified global
117  /// variable or function definition. This should not be passed external (or
118  /// available externally) globals.
119  MCSection *SectionForGlobal(const GlobalObject *GO, SectionKind Kind,
120                              const TargetMachine &TM) const;
121
122  /// This method computes the appropriate section to emit the specified global
123  /// variable or function definition. This should not be passed external (or
124  /// available externally) globals.
125  MCSection *SectionForGlobal(const GlobalObject *GO,
126                              const TargetMachine &TM) const;
127
128  virtual void getNameWithPrefix(SmallVectorImpl<char> &OutName,
129                                 const GlobalValue *GV,
130                                 const TargetMachine &TM) const;
131
132  virtual MCSection *getSectionForJumpTable(const Function &F,
133                                            const TargetMachine &TM) const;
134  virtual MCSection *getSectionForLSDA(const Function &, const MCSymbol &,
135                                       const TargetMachine &) const {
136    return LSDASection;
137  }
138
139  virtual bool shouldPutJumpTableInFunctionSection(bool UsesLabelDifference,
140                                                   const Function &F) const;
141
142  /// Targets should implement this method to assign a section to globals with
143  /// an explicit section specfied. The implementation of this method can
144  /// assume that GO->hasSection() is true.
145  virtual MCSection *
146  getExplicitSectionGlobal(const GlobalObject *GO, SectionKind Kind,
147                           const TargetMachine &TM) const = 0;
148
149  /// Return an MCExpr to use for a reference to the specified global variable
150  /// from exception handling information.
151  virtual const MCExpr *getTTypeGlobalReference(const GlobalValue *GV,
152                                                unsigned Encoding,
153                                                const TargetMachine &TM,
154                                                MachineModuleInfo *MMI,
155                                                MCStreamer &Streamer) const;
156
157  /// Return the MCSymbol for a private symbol with global value name as its
158  /// base, with the specified suffix.
159  MCSymbol *getSymbolWithGlobalValueBase(const GlobalValue *GV,
160                                         StringRef Suffix,
161                                         const TargetMachine &TM) const;
162
163  // The symbol that gets passed to .cfi_personality.
164  virtual MCSymbol *getCFIPersonalitySymbol(const GlobalValue *GV,
165                                            const TargetMachine &TM,
166                                            MachineModuleInfo *MMI) const;
167
168  unsigned getPersonalityEncoding() const { return PersonalityEncoding; }
169  unsigned getLSDAEncoding() const { return LSDAEncoding; }
170  unsigned getTTypeEncoding() const { return TTypeEncoding; }
171  unsigned getCallSiteEncoding() const;
172
173  const MCExpr *getTTypeReference(const MCSymbolRefExpr *Sym, unsigned Encoding,
174                                  MCStreamer &Streamer) const;
175
176  virtual MCSection *getStaticCtorSection(unsigned Priority,
177                                          const MCSymbol *KeySym) const {
178    return StaticCtorSection;
179  }
180
181  virtual MCSection *getStaticDtorSection(unsigned Priority,
182                                          const MCSymbol *KeySym) const {
183    return StaticDtorSection;
184  }
185
186  /// Create a symbol reference to describe the given TLS variable when
187  /// emitting the address in debug info.
188  virtual const MCExpr *getDebugThreadLocalSymbol(const MCSymbol *Sym) const;
189
190  virtual const MCExpr *lowerRelativeReference(const GlobalValue *LHS,
191                                               const GlobalValue *RHS,
192                                               const TargetMachine &TM) const {
193    return nullptr;
194  }
195
196  /// Target supports a native lowering of a dso_local_equivalent constant
197  /// without needing to replace it with equivalent IR.
198  bool supportDSOLocalEquivalentLowering() const {
199    return SupportDSOLocalEquivalentLowering;
200  }
201
202  virtual const MCExpr *lowerDSOLocalEquivalent(const DSOLocalEquivalent *Equiv,
203                                                const TargetMachine &TM) const {
204    return nullptr;
205  }
206
207  /// Target supports replacing a data "PC"-relative access to a symbol
208  /// through another symbol, by accessing the later via a GOT entry instead?
209  bool supportIndirectSymViaGOTPCRel() const {
210    return SupportIndirectSymViaGOTPCRel;
211  }
212
213  /// Target GOT "PC"-relative relocation supports encoding an additional
214  /// binary expression with an offset?
215  bool supportGOTPCRelWithOffset() const {
216    return SupportGOTPCRelWithOffset;
217  }
218
219  /// Target supports TLS offset relocation in debug section?
220  bool supportDebugThreadLocalLocation() const {
221    return SupportDebugThreadLocalLocation;
222  }
223
224  /// Returns the register used as static base in RWPI variants.
225  virtual MCRegister getStaticBase() const { return MCRegister::NoRegister; }
226
227  /// Get the target specific RWPI relocation.
228  virtual const MCExpr *getIndirectSymViaRWPI(const MCSymbol *Sym) const {
229    return nullptr;
230  }
231
232  /// Get the target specific PC relative GOT entry relocation
233  virtual const MCExpr *getIndirectSymViaGOTPCRel(const GlobalValue *GV,
234                                                  const MCSymbol *Sym,
235                                                  const MCValue &MV,
236                                                  int64_t Offset,
237                                                  MachineModuleInfo *MMI,
238                                                  MCStreamer &Streamer) const {
239    return nullptr;
240  }
241
242  /// If supported, return the section to use for the llvm.commandline
243  /// metadata. Otherwise, return nullptr.
244  virtual MCSection *getSectionForCommandLines() const {
245    return nullptr;
246  }
247
248  /// On targets that use separate function descriptor symbols, return a section
249  /// for the descriptor given its symbol. Use only with defined functions.
250  virtual MCSection *
251  getSectionForFunctionDescriptor(const Function *F,
252                                  const TargetMachine &TM) const {
253    return nullptr;
254  }
255
256  /// On targets that support TOC entries, return a section for the entry given
257  /// the symbol it refers to.
258  /// TODO: Implement this interface for existing ELF targets.
259  virtual MCSection *getSectionForTOCEntry(const MCSymbol *S,
260                                           const TargetMachine &TM) const {
261    return nullptr;
262  }
263
264  /// On targets that associate external references with a section, return such
265  /// a section for the given external global.
266  virtual MCSection *
267  getSectionForExternalReference(const GlobalObject *GO,
268                                 const TargetMachine &TM) const {
269    return nullptr;
270  }
271
272  /// Targets that have a special convention for their symbols could use
273  /// this hook to return a specialized symbol.
274  virtual MCSymbol *getTargetSymbol(const GlobalValue *GV,
275                                    const TargetMachine &TM) const {
276    return nullptr;
277  }
278
279  /// If supported, return the function entry point symbol.
280  /// Otherwise, returns nullptr.
281  /// Func must be a function or an alias which has a function as base object.
282  virtual MCSymbol *getFunctionEntryPointSymbol(const GlobalValue *Func,
283                                                const TargetMachine &TM) const {
284    return nullptr;
285  }
286
287protected:
288  virtual MCSection *SelectSectionForGlobal(const GlobalObject *GO,
289                                            SectionKind Kind,
290                                            const TargetMachine &TM) const = 0;
291};
292
293} // end namespace llvm
294
295#endif // LLVM_TARGET_TARGETLOWERINGOBJECTFILE_H
296