xref: /freebsd/contrib/llvm-project/llvm/include/llvm/MC/MCELFStreamer.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
1 //===- MCELFStreamer.h - MCStreamer ELF Object File Interface ---*- C++ -*-===//
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 #ifndef LLVM_MC_MCELFSTREAMER_H
10 #define LLVM_MC_MCELFSTREAMER_H
11 
12 #include "llvm/ADT/SmallVector.h"
13 #include "llvm/MC/MCDirectives.h"
14 #include "llvm/MC/MCELFObjectWriter.h"
15 #include "llvm/MC/MCObjectStreamer.h"
16 
17 namespace llvm {
18 
19 class MCContext;
20 class MCDataFragment;
21 class MCFragment;
22 class MCObjectWriter;
23 class MCSection;
24 class MCSubtargetInfo;
25 class MCSymbol;
26 class MCSymbolRefExpr;
27 class MCAsmBackend;
28 class MCCodeEmitter;
29 class MCExpr;
30 class MCInst;
31 
32 class MCELFStreamer : public MCObjectStreamer {
33 public:
34   MCELFStreamer(MCContext &Context, std::unique_ptr<MCAsmBackend> TAB,
35                 std::unique_ptr<MCObjectWriter> OW,
36                 std::unique_ptr<MCCodeEmitter> Emitter);
37 
38   ~MCELFStreamer() override = default;
39 
40   /// state management
reset()41   void reset() override {
42     SeenIdent = false;
43     MCObjectStreamer::reset();
44   }
45 
46   ELFObjectWriter &getWriter();
47 
48   /// \name MCStreamer Interface
49   /// @{
50 
51   void initSections(bool NoExecStack, const MCSubtargetInfo &STI) override;
52   void changeSection(MCSection *Section, uint32_t Subsection = 0) override;
53   void emitLabel(MCSymbol *Symbol, SMLoc Loc = SMLoc()) override;
54   void emitLabelAtPos(MCSymbol *Symbol, SMLoc Loc, MCDataFragment &F,
55                       uint64_t Offset) override;
56   void emitAssemblerFlag(MCAssemblerFlag Flag) override;
57   void emitThumbFunc(MCSymbol *Func) override;
58   void emitWeakReference(MCSymbol *Alias, const MCSymbol *Symbol) override;
59   bool emitSymbolAttribute(MCSymbol *Symbol, MCSymbolAttr Attribute) override;
60   void emitSymbolDesc(MCSymbol *Symbol, unsigned DescValue) override;
61   void emitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
62                         Align ByteAlignment) override;
63 
64   void emitELFSize(MCSymbol *Symbol, const MCExpr *Value) override;
65   void emitELFSymverDirective(const MCSymbol *OriginalSym, StringRef Name,
66                               bool KeepOriginalSym) override;
67 
68   void emitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
69                              Align ByteAlignment) override;
70 
71   void emitZerofill(MCSection *Section, MCSymbol *Symbol = nullptr,
72                     uint64_t Size = 0, Align ByteAlignment = Align(1),
73                     SMLoc L = SMLoc()) override;
74   void emitTBSSSymbol(MCSection *Section, MCSymbol *Symbol, uint64_t Size,
75                       Align ByteAlignment = Align(1)) override;
76   void emitValueImpl(const MCExpr *Value, unsigned Size,
77                      SMLoc Loc = SMLoc()) override;
78 
79   void emitIdent(StringRef IdentString) override;
80 
81   void emitValueToAlignment(Align, int64_t, unsigned, unsigned) override;
82 
83   void emitCGProfileEntry(const MCSymbolRefExpr *From,
84                           const MCSymbolRefExpr *To, uint64_t Count) override;
85 
86   // This is final. Override MCTargetStreamer::finish instead for
87   // target-specific code.
88   void finishImpl() final;
89 
90   void emitBundleAlignMode(Align Alignment) override;
91   void emitBundleLock(bool AlignToEnd) override;
92   void emitBundleUnlock() override;
93 
94   /// ELF object attributes section emission support
95   struct AttributeItem {
96     // This structure holds all attributes, accounting for their string /
97     // numeric value, so we can later emit them in declaration order, keeping
98     // all in the same vector.
99     enum {
100       HiddenAttribute = 0,
101       NumericAttribute,
102       TextAttribute,
103       NumericAndTextAttributes
104     } Type;
105     unsigned Tag;
106     unsigned IntValue;
107     std::string StringValue;
108   };
109 
110   // Attributes that are added and managed entirely by target.
111   SmallVector<AttributeItem, 64> Contents;
112   void setAttributeItem(unsigned Attribute, unsigned Value,
113                         bool OverwriteExisting);
114   void setAttributeItem(unsigned Attribute, StringRef Value,
115                         bool OverwriteExisting);
116   void setAttributeItems(unsigned Attribute, unsigned IntValue,
117                          StringRef StringValue, bool OverwriteExisting);
emitAttributesSection(StringRef Vendor,const Twine & Section,unsigned Type,MCSection * & AttributeSection)118   void emitAttributesSection(StringRef Vendor, const Twine &Section,
119                              unsigned Type, MCSection *&AttributeSection) {
120     createAttributesSection(Vendor, Section, Type, AttributeSection, Contents);
121   }
122 
123 private:
124   AttributeItem *getAttributeItem(unsigned Attribute);
125   size_t calculateContentSize(SmallVector<AttributeItem, 64> &AttrsVec);
126   void createAttributesSection(StringRef Vendor, const Twine &Section,
127                                unsigned Type, MCSection *&AttributeSection,
128                                SmallVector<AttributeItem, 64> &AttrsVec);
129 
130   // GNU attributes that will get emitted at the end of the asm file.
131   SmallVector<AttributeItem, 64> GNUAttributes;
132 
133 public:
emitGNUAttribute(unsigned Tag,unsigned Value)134   void emitGNUAttribute(unsigned Tag, unsigned Value) override {
135     AttributeItem Item = {AttributeItem::NumericAttribute, Tag, Value,
136                           std::string(StringRef(""))};
137     GNUAttributes.push_back(Item);
138   }
139 
140 private:
141   bool isBundleLocked() const;
142   void emitInstToFragment(const MCInst &Inst, const MCSubtargetInfo &) override;
143   void emitInstToData(const MCInst &Inst, const MCSubtargetInfo &) override;
144 
145   void fixSymbolsInTLSFixups(const MCExpr *expr);
146   void finalizeCGProfileEntry(const MCSymbolRefExpr *&S, uint64_t Offset);
147   void finalizeCGProfile();
148 
149   bool SeenIdent = false;
150 };
151 
152 MCELFStreamer *createARMELFStreamer(MCContext &Context,
153                                     std::unique_ptr<MCAsmBackend> TAB,
154                                     std::unique_ptr<MCObjectWriter> OW,
155                                     std::unique_ptr<MCCodeEmitter> Emitter,
156                                     bool IsThumb, bool IsAndroid);
157 
158 } // end namespace llvm
159 
160 #endif // LLVM_MC_MCELFSTREAMER_H
161