MCAssembler.h revision 6a3cbc35a75468d565385a0db8e7051478f383f4
1674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen//===- MCAssembler.h - Object File Generation -------------------*- C++ -*-===// 2674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// 3674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// The LLVM Compiler Infrastructure 4674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// 5674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// This file is distributed under the University of Illinois Open Source 6674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// License. See LICENSE.TXT for details. 7674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen// 8674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen//===----------------------------------------------------------------------===// 9674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 10674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#ifndef LLVM_MC_MCASSEMBLER_H 11674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#define LLVM_MC_MCASSEMBLER_H 12674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 13674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/ADT/DenseMap.h" 14674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/ADT/SmallPtrSet.h" 15674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/ADT/SmallString.h" 16674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/ADT/ilist.h" 17674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/ADT/ilist_node.h" 18674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/MC/MCFixup.h" 19674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/MC/MCInst.h" 20674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/Support/Casting.h" 21674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include "llvm/Support/DataTypes.h" 22674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen#include <vector> // FIXME: Shouldn't be needed. 23674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 24674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogennamespace llvm { 25674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass raw_ostream; 26674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCAsmLayout; 27674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCAssembler; 28674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCContext; 29674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCCodeEmitter; 30674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCExpr; 31674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCFragment; 32674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCObjectWriter; 33674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCSection; 34674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCSectionData; 35674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCSymbol; 36674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCSymbolData; 37674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCValue; 38674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCAsmBackend; 39674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 40674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCFragment : public ilist_node<MCFragment> { 41674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen friend class MCAsmLayout; 42674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 43674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCFragment(const MCFragment&) LLVM_DELETED_FUNCTION; 44674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen void operator=(const MCFragment&) LLVM_DELETED_FUNCTION; 45674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 46674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenpublic: 47674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen enum FragmentType { 48674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Align, 49674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Data, 50674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_CompactEncodedInst, 51674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Fill, 52674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Relaxable, 53674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Org, 54674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_Dwarf, 55674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_DwarfFrame, 56674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FT_LEB 57674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen }; 58674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 59674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenprivate: 60674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FragmentType Kind; 61674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 62674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// Parent - The data for the section this fragment is in. 63674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCSectionData *Parent; 64674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 65674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// Atom - The atom this fragment is in, as represented by it's defining 66674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// symbol. Atom's are only used by backends which set 67674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// \see MCAsmBackend::hasReliableSymbolDifference(). 68674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCSymbolData *Atom; 69674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 70674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// @name Assembler Backend Data 71674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// @{ 72674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen // 73674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen // FIXME: This could all be kept private to the assembler implementation. 74674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 75674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// Offset - The offset of this fragment in its section. This is ~0 until 76674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// initialized. 77674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen uint64_t Offset; 78674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 79674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// LayoutOrder - The layout order of this fragment. 80674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen unsigned LayoutOrder; 81674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 82674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// @} 83674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 84674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenprotected: 85674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCFragment(FragmentType _Kind, MCSectionData *_Parent = 0); 86674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 87674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenpublic: 88674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen // Only for sentinel. 89674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCFragment(); 90674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual ~MCFragment(); 91674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 92674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen FragmentType getKind() const { return Kind; } 93674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 94674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCSectionData *getParent() const { return Parent; } 95674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen void setParent(MCSectionData *Value) { Parent = Value; } 96674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 97674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCSymbolData *getAtom() const { return Atom; } 98674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen void setAtom(MCSymbolData *Value) { Atom = Value; } 99674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 100674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen unsigned getLayoutOrder() const { return LayoutOrder; } 101674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen void setLayoutOrder(unsigned Value) { LayoutOrder = Value; } 102674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 103674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// \brief Does this fragment have instructions emitted into it? By default 104674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// this is false, but specific fragment types may set it to true. 105674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual bool hasInstructions() const { return false; } 106674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 107674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// \brief Should this fragment be placed at the end of an aligned bundle? 108674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual bool alignToBundleEnd() const { return false; } 109674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual void setAlignToBundleEnd(bool V) { } 110674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 111674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// \brief Get the padding size that must be inserted before this fragment. 112674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// Used for bundling. By default, no padding is inserted. 113674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// Note that padding size is restricted to 8 bits. This is an optimization 114674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// to reduce the amount of space used for each fragment. In practice, larger 115674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// padding should never be required. 116674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual uint8_t getBundlePadding() const { 117674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen return 0; 118674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 119674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 120674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// \brief Set the padding size for this fragment. By default it's a no-op, 121674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen /// and only some fragments have a meaningful implementation. 122674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual void setBundlePadding(uint8_t N) { 123674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 124674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 125674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen void dump(); 126674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen}; 127674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 128674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// Interface implemented by fragments that contain encoded instructions and/or 129674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// data. 130674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// 131674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCEncodedFragment : public MCFragment { 132674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual void anchor(); 133674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 134674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen uint8_t BundlePadding; 135674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenpublic: 136674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCEncodedFragment(MCFragment::FragmentType FType, MCSectionData *SD = 0) 137674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen : MCFragment(FType, SD), BundlePadding(0) 138674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen { 139674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 140674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual ~MCEncodedFragment(); 141674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 142674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual SmallVectorImpl<char> &getContents() = 0; 143674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual const SmallVectorImpl<char> &getContents() const = 0; 144674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 145674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual uint8_t getBundlePadding() const { 146674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen return BundlePadding; 147674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 148674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 149674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual void setBundlePadding(uint8_t N) { 150674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen BundlePadding = N; 151674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 152674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 153674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen static bool classof(const MCFragment *F) { 154674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCFragment::FragmentType Kind = F->getKind(); 155674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen switch (Kind) { 156674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen default: 157674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen return false; 158674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen case MCFragment::FT_Relaxable: 159674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen case MCFragment::FT_CompactEncodedInst: 160674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen case MCFragment::FT_Data: 161674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen return true; 162674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 163674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 164674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen}; 165674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 166674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// Interface implemented by fragments that contain encoded instructions and/or 167674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// data and also have fixups registered. 168674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen/// 169674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenclass MCEncodedFragmentWithFixups : public MCEncodedFragment { 170674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual void anchor(); 171674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 172674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogenpublic: 173674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCEncodedFragmentWithFixups(MCFragment::FragmentType FType, 174674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCSectionData *SD = 0) 175674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen : MCEncodedFragment(FType, SD) 176674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen { 177674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen } 178674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 179674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual ~MCEncodedFragmentWithFixups(); 180674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 181674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen typedef SmallVectorImpl<MCFixup>::const_iterator const_fixup_iterator; 182674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen typedef SmallVectorImpl<MCFixup>::iterator fixup_iterator; 183674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 184674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual SmallVectorImpl<MCFixup> &getFixups() = 0; 185674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual const SmallVectorImpl<MCFixup> &getFixups() const = 0; 186674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 187674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual fixup_iterator fixup_begin() = 0; 188674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual const_fixup_iterator fixup_begin() const = 0; 189674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual fixup_iterator fixup_end() = 0; 190674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen virtual const_fixup_iterator fixup_end() const = 0; 191674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen 192674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen static bool classof(const MCFragment *F) { 193674060f01e9090cd21b3c5656cc3204912ad17a6Jon Boekenoogen MCFragment::FragmentType Kind = F->getKind(); 194 return Kind == MCFragment::FT_Relaxable || Kind == MCFragment::FT_Data; 195 } 196}; 197 198/// Fragment for data and encoded instructions. 199/// 200class MCDataFragment : public MCEncodedFragmentWithFixups { 201 virtual void anchor(); 202 203 /// \brief Does this fragment contain encoded instructions anywhere in it? 204 bool HasInstructions; 205 206 /// \brief Should this fragment be aligned to the end of a bundle? 207 bool AlignToBundleEnd; 208 209 SmallVector<char, 32> Contents; 210 211 /// Fixups - The list of fixups in this fragment. 212 SmallVector<MCFixup, 4> Fixups; 213public: 214 MCDataFragment(MCSectionData *SD = 0) 215 : MCEncodedFragmentWithFixups(FT_Data, SD), 216 HasInstructions(false), AlignToBundleEnd(false) 217 { 218 } 219 220 virtual SmallVectorImpl<char> &getContents() { return Contents; } 221 virtual const SmallVectorImpl<char> &getContents() const { return Contents; } 222 223 SmallVectorImpl<MCFixup> &getFixups() { 224 return Fixups; 225 } 226 227 const SmallVectorImpl<MCFixup> &getFixups() const { 228 return Fixups; 229 } 230 231 virtual bool hasInstructions() const { return HasInstructions; } 232 virtual void setHasInstructions(bool V) { HasInstructions = V; } 233 234 virtual bool alignToBundleEnd() const { return AlignToBundleEnd; } 235 virtual void setAlignToBundleEnd(bool V) { AlignToBundleEnd = V; } 236 237 fixup_iterator fixup_begin() { return Fixups.begin(); } 238 const_fixup_iterator fixup_begin() const { return Fixups.begin(); } 239 240 fixup_iterator fixup_end() {return Fixups.end();} 241 const_fixup_iterator fixup_end() const {return Fixups.end();} 242 243 static bool classof(const MCFragment *F) { 244 return F->getKind() == MCFragment::FT_Data; 245 } 246}; 247 248/// This is a compact (memory-size-wise) fragment for holding an encoded 249/// instruction (non-relaxable) that has no fixups registered. When applicable, 250/// it can be used instead of MCDataFragment and lead to lower memory 251/// consumption. 252/// 253class MCCompactEncodedInstFragment : public MCEncodedFragment { 254 virtual void anchor(); 255 256 /// \brief Should this fragment be aligned to the end of a bundle? 257 bool AlignToBundleEnd; 258 259 SmallVector<char, 4> Contents; 260public: 261 MCCompactEncodedInstFragment(MCSectionData *SD = 0) 262 : MCEncodedFragment(FT_CompactEncodedInst, SD), AlignToBundleEnd(false) 263 { 264 } 265 266 virtual bool hasInstructions() const { 267 return true; 268 } 269 270 virtual SmallVectorImpl<char> &getContents() { return Contents; } 271 virtual const SmallVectorImpl<char> &getContents() const { return Contents; } 272 273 virtual bool alignToBundleEnd() const { return AlignToBundleEnd; } 274 virtual void setAlignToBundleEnd(bool V) { AlignToBundleEnd = V; } 275 276 static bool classof(const MCFragment *F) { 277 return F->getKind() == MCFragment::FT_CompactEncodedInst; 278 } 279}; 280 281/// A relaxable fragment holds on to its MCInst, since it may need to be 282/// relaxed during the assembler layout and relaxation stage. 283/// 284class MCRelaxableFragment : public MCEncodedFragmentWithFixups { 285 virtual void anchor(); 286 287 /// Inst - The instruction this is a fragment for. 288 MCInst Inst; 289 290 /// Contents - Binary data for the currently encoded instruction. 291 SmallVector<char, 8> Contents; 292 293 /// Fixups - The list of fixups in this fragment. 294 SmallVector<MCFixup, 1> Fixups; 295 296public: 297 MCRelaxableFragment(const MCInst &_Inst, MCSectionData *SD = 0) 298 : MCEncodedFragmentWithFixups(FT_Relaxable, SD), Inst(_Inst) { 299 } 300 301 virtual SmallVectorImpl<char> &getContents() { return Contents; } 302 virtual const SmallVectorImpl<char> &getContents() const { return Contents; } 303 304 const MCInst &getInst() const { return Inst; } 305 void setInst(const MCInst& Value) { Inst = Value; } 306 307 SmallVectorImpl<MCFixup> &getFixups() { 308 return Fixups; 309 } 310 311 const SmallVectorImpl<MCFixup> &getFixups() const { 312 return Fixups; 313 } 314 315 virtual bool hasInstructions() const { return true; } 316 317 fixup_iterator fixup_begin() { return Fixups.begin(); } 318 const_fixup_iterator fixup_begin() const { return Fixups.begin(); } 319 320 fixup_iterator fixup_end() {return Fixups.end();} 321 const_fixup_iterator fixup_end() const {return Fixups.end();} 322 323 static bool classof(const MCFragment *F) { 324 return F->getKind() == MCFragment::FT_Relaxable; 325 } 326}; 327 328class MCAlignFragment : public MCFragment { 329 virtual void anchor(); 330 331 /// Alignment - The alignment to ensure, in bytes. 332 unsigned Alignment; 333 334 /// Value - Value to use for filling padding bytes. 335 int64_t Value; 336 337 /// ValueSize - The size of the integer (in bytes) of \p Value. 338 unsigned ValueSize; 339 340 /// MaxBytesToEmit - The maximum number of bytes to emit; if the alignment 341 /// cannot be satisfied in this width then this fragment is ignored. 342 unsigned MaxBytesToEmit; 343 344 /// EmitNops - Flag to indicate that (optimal) NOPs should be emitted instead 345 /// of using the provided value. The exact interpretation of this flag is 346 /// target dependent. 347 bool EmitNops : 1; 348 349public: 350 MCAlignFragment(unsigned _Alignment, int64_t _Value, unsigned _ValueSize, 351 unsigned _MaxBytesToEmit, MCSectionData *SD = 0) 352 : MCFragment(FT_Align, SD), Alignment(_Alignment), 353 Value(_Value),ValueSize(_ValueSize), 354 MaxBytesToEmit(_MaxBytesToEmit), EmitNops(false) {} 355 356 /// @name Accessors 357 /// @{ 358 359 unsigned getAlignment() const { return Alignment; } 360 361 int64_t getValue() const { return Value; } 362 363 unsigned getValueSize() const { return ValueSize; } 364 365 unsigned getMaxBytesToEmit() const { return MaxBytesToEmit; } 366 367 bool hasEmitNops() const { return EmitNops; } 368 void setEmitNops(bool Value) { EmitNops = Value; } 369 370 /// @} 371 372 static bool classof(const MCFragment *F) { 373 return F->getKind() == MCFragment::FT_Align; 374 } 375}; 376 377class MCFillFragment : public MCFragment { 378 virtual void anchor(); 379 380 /// Value - Value to use for filling bytes. 381 int64_t Value; 382 383 /// ValueSize - The size (in bytes) of \p Value to use when filling, or 0 if 384 /// this is a virtual fill fragment. 385 unsigned ValueSize; 386 387 /// Size - The number of bytes to insert. 388 uint64_t Size; 389 390public: 391 MCFillFragment(int64_t _Value, unsigned _ValueSize, uint64_t _Size, 392 MCSectionData *SD = 0) 393 : MCFragment(FT_Fill, SD), 394 Value(_Value), ValueSize(_ValueSize), Size(_Size) { 395 assert((!ValueSize || (Size % ValueSize) == 0) && 396 "Fill size must be a multiple of the value size!"); 397 } 398 399 /// @name Accessors 400 /// @{ 401 402 int64_t getValue() const { return Value; } 403 404 unsigned getValueSize() const { return ValueSize; } 405 406 uint64_t getSize() const { return Size; } 407 408 /// @} 409 410 static bool classof(const MCFragment *F) { 411 return F->getKind() == MCFragment::FT_Fill; 412 } 413}; 414 415class MCOrgFragment : public MCFragment { 416 virtual void anchor(); 417 418 /// Offset - The offset this fragment should start at. 419 const MCExpr *Offset; 420 421 /// Value - Value to use for filling bytes. 422 int8_t Value; 423 424public: 425 MCOrgFragment(const MCExpr &_Offset, int8_t _Value, MCSectionData *SD = 0) 426 : MCFragment(FT_Org, SD), 427 Offset(&_Offset), Value(_Value) {} 428 429 /// @name Accessors 430 /// @{ 431 432 const MCExpr &getOffset() const { return *Offset; } 433 434 uint8_t getValue() const { return Value; } 435 436 /// @} 437 438 static bool classof(const MCFragment *F) { 439 return F->getKind() == MCFragment::FT_Org; 440 } 441}; 442 443class MCLEBFragment : public MCFragment { 444 virtual void anchor(); 445 446 /// Value - The value this fragment should contain. 447 const MCExpr *Value; 448 449 /// IsSigned - True if this is a sleb128, false if uleb128. 450 bool IsSigned; 451 452 SmallString<8> Contents; 453public: 454 MCLEBFragment(const MCExpr &Value_, bool IsSigned_, MCSectionData *SD) 455 : MCFragment(FT_LEB, SD), 456 Value(&Value_), IsSigned(IsSigned_) { Contents.push_back(0); } 457 458 /// @name Accessors 459 /// @{ 460 461 const MCExpr &getValue() const { return *Value; } 462 463 bool isSigned() const { return IsSigned; } 464 465 SmallString<8> &getContents() { return Contents; } 466 const SmallString<8> &getContents() const { return Contents; } 467 468 /// @} 469 470 static bool classof(const MCFragment *F) { 471 return F->getKind() == MCFragment::FT_LEB; 472 } 473}; 474 475class MCDwarfLineAddrFragment : public MCFragment { 476 virtual void anchor(); 477 478 /// LineDelta - the value of the difference between the two line numbers 479 /// between two .loc dwarf directives. 480 int64_t LineDelta; 481 482 /// AddrDelta - The expression for the difference of the two symbols that 483 /// make up the address delta between two .loc dwarf directives. 484 const MCExpr *AddrDelta; 485 486 SmallString<8> Contents; 487 488public: 489 MCDwarfLineAddrFragment(int64_t _LineDelta, const MCExpr &_AddrDelta, 490 MCSectionData *SD) 491 : MCFragment(FT_Dwarf, SD), 492 LineDelta(_LineDelta), AddrDelta(&_AddrDelta) { Contents.push_back(0); } 493 494 /// @name Accessors 495 /// @{ 496 497 int64_t getLineDelta() const { return LineDelta; } 498 499 const MCExpr &getAddrDelta() const { return *AddrDelta; } 500 501 SmallString<8> &getContents() { return Contents; } 502 const SmallString<8> &getContents() const { return Contents; } 503 504 /// @} 505 506 static bool classof(const MCFragment *F) { 507 return F->getKind() == MCFragment::FT_Dwarf; 508 } 509}; 510 511class MCDwarfCallFrameFragment : public MCFragment { 512 virtual void anchor(); 513 514 /// AddrDelta - The expression for the difference of the two symbols that 515 /// make up the address delta between two .cfi_* dwarf directives. 516 const MCExpr *AddrDelta; 517 518 SmallString<8> Contents; 519 520public: 521 MCDwarfCallFrameFragment(const MCExpr &_AddrDelta, MCSectionData *SD) 522 : MCFragment(FT_DwarfFrame, SD), 523 AddrDelta(&_AddrDelta) { Contents.push_back(0); } 524 525 /// @name Accessors 526 /// @{ 527 528 const MCExpr &getAddrDelta() const { return *AddrDelta; } 529 530 SmallString<8> &getContents() { return Contents; } 531 const SmallString<8> &getContents() const { return Contents; } 532 533 /// @} 534 535 static bool classof(const MCFragment *F) { 536 return F->getKind() == MCFragment::FT_DwarfFrame; 537 } 538}; 539 540// FIXME: Should this be a separate class, or just merged into MCSection? Since 541// we anticipate the fast path being through an MCAssembler, the only reason to 542// keep it out is for API abstraction. 543class MCSectionData : public ilist_node<MCSectionData> { 544 friend class MCAsmLayout; 545 546 MCSectionData(const MCSectionData&) LLVM_DELETED_FUNCTION; 547 void operator=(const MCSectionData&) LLVM_DELETED_FUNCTION; 548 549public: 550 typedef iplist<MCFragment> FragmentListType; 551 552 typedef FragmentListType::const_iterator const_iterator; 553 typedef FragmentListType::iterator iterator; 554 555 typedef FragmentListType::const_reverse_iterator const_reverse_iterator; 556 typedef FragmentListType::reverse_iterator reverse_iterator; 557 558 /// \brief Express the state of bundle locked groups while emitting code. 559 enum BundleLockStateType { 560 NotBundleLocked, 561 BundleLocked, 562 BundleLockedAlignToEnd 563 }; 564private: 565 FragmentListType Fragments; 566 const MCSection *Section; 567 568 /// Ordinal - The section index in the assemblers section list. 569 unsigned Ordinal; 570 571 /// LayoutOrder - The index of this section in the layout order. 572 unsigned LayoutOrder; 573 574 /// Alignment - The maximum alignment seen in this section. 575 unsigned Alignment; 576 577 /// \brief Keeping track of bundle-locked state. 578 BundleLockStateType BundleLockState; 579 580 /// \brief We've seen a bundle_lock directive but not its first instruction 581 /// yet. 582 bool BundleGroupBeforeFirstInst; 583 584 /// @name Assembler Backend Data 585 /// @{ 586 // 587 // FIXME: This could all be kept private to the assembler implementation. 588 589 /// HasInstructions - Whether this section has had instructions emitted into 590 /// it. 591 unsigned HasInstructions : 1; 592 593 /// @} 594 595public: 596 // Only for use as sentinel. 597 MCSectionData(); 598 MCSectionData(const MCSection &Section, MCAssembler *A = 0); 599 600 const MCSection &getSection() const { return *Section; } 601 602 unsigned getAlignment() const { return Alignment; } 603 void setAlignment(unsigned Value) { Alignment = Value; } 604 605 bool hasInstructions() const { return HasInstructions; } 606 void setHasInstructions(bool Value) { HasInstructions = Value; } 607 608 unsigned getOrdinal() const { return Ordinal; } 609 void setOrdinal(unsigned Value) { Ordinal = Value; } 610 611 unsigned getLayoutOrder() const { return LayoutOrder; } 612 void setLayoutOrder(unsigned Value) { LayoutOrder = Value; } 613 614 /// @name Fragment Access 615 /// @{ 616 617 const FragmentListType &getFragmentList() const { return Fragments; } 618 FragmentListType &getFragmentList() { return Fragments; } 619 620 iterator begin() { return Fragments.begin(); } 621 const_iterator begin() const { return Fragments.begin(); } 622 623 iterator end() { return Fragments.end(); } 624 const_iterator end() const { return Fragments.end(); } 625 626 reverse_iterator rbegin() { return Fragments.rbegin(); } 627 const_reverse_iterator rbegin() const { return Fragments.rbegin(); } 628 629 reverse_iterator rend() { return Fragments.rend(); } 630 const_reverse_iterator rend() const { return Fragments.rend(); } 631 632 size_t size() const { return Fragments.size(); } 633 634 bool empty() const { return Fragments.empty(); } 635 636 bool isBundleLocked() const { 637 return BundleLockState != NotBundleLocked; 638 } 639 640 BundleLockStateType getBundleLockState() const { 641 return BundleLockState; 642 } 643 644 void setBundleLockState(BundleLockStateType NewState) { 645 BundleLockState = NewState; 646 } 647 648 bool isBundleGroupBeforeFirstInst() const { 649 return BundleGroupBeforeFirstInst; 650 } 651 652 void setBundleGroupBeforeFirstInst(bool IsFirst) { 653 BundleGroupBeforeFirstInst = IsFirst; 654 } 655 656 void dump(); 657 658 /// @} 659}; 660 661// FIXME: Same concerns as with SectionData. 662class MCSymbolData : public ilist_node<MCSymbolData> { 663public: 664 const MCSymbol *Symbol; 665 666 /// Fragment - The fragment this symbol's value is relative to, if any. 667 MCFragment *Fragment; 668 669 /// Offset - The offset to apply to the fragment address to form this symbol's 670 /// value. 671 uint64_t Offset; 672 673 /// IsExternal - True if this symbol is visible outside this translation 674 /// unit. 675 unsigned IsExternal : 1; 676 677 /// IsPrivateExtern - True if this symbol is private extern. 678 unsigned IsPrivateExtern : 1; 679 680 /// CommonSize - The size of the symbol, if it is 'common', or 0. 681 // 682 // FIXME: Pack this in with other fields? We could put it in offset, since a 683 // common symbol can never get a definition. 684 uint64_t CommonSize; 685 686 /// SymbolSize - An expression describing how to calculate the size of 687 /// a symbol. If a symbol has no size this field will be NULL. 688 const MCExpr *SymbolSize; 689 690 /// CommonAlign - The alignment of the symbol, if it is 'common'. 691 // 692 // FIXME: Pack this in with other fields? 693 unsigned CommonAlign; 694 695 /// Flags - The Flags field is used by object file implementations to store 696 /// additional per symbol information which is not easily classified. 697 uint32_t Flags; 698 699 /// Index - Index field, for use by the object file implementation. 700 uint64_t Index; 701 702public: 703 // Only for use as sentinel. 704 MCSymbolData(); 705 MCSymbolData(const MCSymbol &_Symbol, MCFragment *_Fragment, uint64_t _Offset, 706 MCAssembler *A = 0); 707 708 /// @name Accessors 709 /// @{ 710 711 const MCSymbol &getSymbol() const { return *Symbol; } 712 713 MCFragment *getFragment() const { return Fragment; } 714 void setFragment(MCFragment *Value) { Fragment = Value; } 715 716 uint64_t getOffset() const { return Offset; } 717 void setOffset(uint64_t Value) { Offset = Value; } 718 719 /// @} 720 /// @name Symbol Attributes 721 /// @{ 722 723 bool isExternal() const { return IsExternal; } 724 void setExternal(bool Value) { IsExternal = Value; } 725 726 bool isPrivateExtern() const { return IsPrivateExtern; } 727 void setPrivateExtern(bool Value) { IsPrivateExtern = Value; } 728 729 /// isCommon - Is this a 'common' symbol. 730 bool isCommon() const { return CommonSize != 0; } 731 732 /// setCommon - Mark this symbol as being 'common'. 733 /// 734 /// \param Size - The size of the symbol. 735 /// \param Align - The alignment of the symbol. 736 void setCommon(uint64_t Size, unsigned Align) { 737 CommonSize = Size; 738 CommonAlign = Align; 739 } 740 741 /// getCommonSize - Return the size of a 'common' symbol. 742 uint64_t getCommonSize() const { 743 assert(isCommon() && "Not a 'common' symbol!"); 744 return CommonSize; 745 } 746 747 void setSize(const MCExpr *SS) { 748 SymbolSize = SS; 749 } 750 751 const MCExpr *getSize() const { 752 return SymbolSize; 753 } 754 755 756 /// getCommonAlignment - Return the alignment of a 'common' symbol. 757 unsigned getCommonAlignment() const { 758 assert(isCommon() && "Not a 'common' symbol!"); 759 return CommonAlign; 760 } 761 762 /// getFlags - Get the (implementation defined) symbol flags. 763 uint32_t getFlags() const { return Flags; } 764 765 /// setFlags - Set the (implementation defined) symbol flags. 766 void setFlags(uint32_t Value) { Flags = Value; } 767 768 /// modifyFlags - Modify the flags via a mask 769 void modifyFlags(uint32_t Value, uint32_t Mask) { 770 Flags = (Flags & ~Mask) | Value; 771 } 772 773 /// getIndex - Get the (implementation defined) index. 774 uint64_t getIndex() const { return Index; } 775 776 /// setIndex - Set the (implementation defined) index. 777 void setIndex(uint64_t Value) { Index = Value; } 778 779 /// @} 780 781 void dump(); 782}; 783 784// FIXME: This really doesn't belong here. See comments below. 785struct IndirectSymbolData { 786 MCSymbol *Symbol; 787 MCSectionData *SectionData; 788}; 789 790// FIXME: Ditto this. Purely so the Streamer and the ObjectWriter can talk 791// to one another. 792struct DataRegionData { 793 // This enum should be kept in sync w/ the mach-o definition in 794 // llvm/Object/MachOFormat.h. 795 enum KindTy { Data = 1, JumpTable8, JumpTable16, JumpTable32 } Kind; 796 MCSymbol *Start; 797 MCSymbol *End; 798}; 799 800class MCAssembler { 801 friend class MCAsmLayout; 802 803public: 804 typedef iplist<MCSectionData> SectionDataListType; 805 typedef iplist<MCSymbolData> SymbolDataListType; 806 807 typedef SectionDataListType::const_iterator const_iterator; 808 typedef SectionDataListType::iterator iterator; 809 810 typedef SymbolDataListType::const_iterator const_symbol_iterator; 811 typedef SymbolDataListType::iterator symbol_iterator; 812 813 typedef std::vector<IndirectSymbolData>::const_iterator 814 const_indirect_symbol_iterator; 815 typedef std::vector<IndirectSymbolData>::iterator indirect_symbol_iterator; 816 817 typedef std::vector<DataRegionData>::const_iterator 818 const_data_region_iterator; 819 typedef std::vector<DataRegionData>::iterator data_region_iterator; 820 821private: 822 MCAssembler(const MCAssembler&) LLVM_DELETED_FUNCTION; 823 void operator=(const MCAssembler&) LLVM_DELETED_FUNCTION; 824 825 MCContext &Context; 826 827 MCAsmBackend &Backend; 828 829 MCCodeEmitter &Emitter; 830 831 MCObjectWriter &Writer; 832 833 raw_ostream &OS; 834 835 iplist<MCSectionData> Sections; 836 837 iplist<MCSymbolData> Symbols; 838 839 /// The map of sections to their associated assembler backend data. 840 // 841 // FIXME: Avoid this indirection? 842 DenseMap<const MCSection*, MCSectionData*> SectionMap; 843 844 /// The map of symbols to their associated assembler backend data. 845 // 846 // FIXME: Avoid this indirection? 847 DenseMap<const MCSymbol*, MCSymbolData*> SymbolMap; 848 849 std::vector<IndirectSymbolData> IndirectSymbols; 850 851 std::vector<DataRegionData> DataRegions; 852 /// The set of function symbols for which a .thumb_func directive has 853 /// been seen. 854 // 855 // FIXME: We really would like this in target specific code rather than 856 // here. Maybe when the relocation stuff moves to target specific, 857 // this can go with it? The streamer would need some target specific 858 // refactoring too. 859 SmallPtrSet<const MCSymbol*, 64> ThumbFuncs; 860 861 /// \brief The bundle alignment size currently set in the assembler. 862 /// 863 /// By default it's 0, which means bundling is disabled. 864 unsigned BundleAlignSize; 865 866 unsigned RelaxAll : 1; 867 unsigned NoExecStack : 1; 868 unsigned SubsectionsViaSymbols : 1; 869 870private: 871 /// Evaluate a fixup to a relocatable expression and the value which should be 872 /// placed into the fixup. 873 /// 874 /// \param Layout The layout to use for evaluation. 875 /// \param Fixup The fixup to evaluate. 876 /// \param DF The fragment the fixup is inside. 877 /// \param Target [out] On return, the relocatable expression the fixup 878 /// evaluates to. 879 /// \param Value [out] On return, the value of the fixup as currently laid 880 /// out. 881 /// \return Whether the fixup value was fully resolved. This is true if the 882 /// \p Value result is fixed, otherwise the value may change due to 883 /// relocation. 884 bool evaluateFixup(const MCAsmLayout &Layout, 885 const MCFixup &Fixup, const MCFragment *DF, 886 MCValue &Target, uint64_t &Value) const; 887 888 /// Check whether a fixup can be satisfied, or whether it needs to be relaxed 889 /// (increased in size, in order to hold its value correctly). 890 bool fixupNeedsRelaxation(const MCFixup &Fixup, const MCRelaxableFragment *DF, 891 const MCAsmLayout &Layout) const; 892 893 /// Check whether the given fragment needs relaxation. 894 bool fragmentNeedsRelaxation(const MCRelaxableFragment *IF, 895 const MCAsmLayout &Layout) const; 896 897 /// \brief Perform one layout iteration and return true if any offsets 898 /// were adjusted. 899 bool layoutOnce(MCAsmLayout &Layout); 900 901 /// \brief Perform one layout iteration of the given section and return true 902 /// if any offsets were adjusted. 903 bool layoutSectionOnce(MCAsmLayout &Layout, MCSectionData &SD); 904 905 bool relaxInstruction(MCAsmLayout &Layout, MCRelaxableFragment &IF); 906 907 bool relaxLEB(MCAsmLayout &Layout, MCLEBFragment &IF); 908 909 bool relaxDwarfLineAddr(MCAsmLayout &Layout, MCDwarfLineAddrFragment &DF); 910 bool relaxDwarfCallFrameFragment(MCAsmLayout &Layout, 911 MCDwarfCallFrameFragment &DF); 912 913 /// finishLayout - Finalize a layout, including fragment lowering. 914 void finishLayout(MCAsmLayout &Layout); 915 916 uint64_t handleFixup(const MCAsmLayout &Layout, 917 MCFragment &F, const MCFixup &Fixup); 918 919public: 920 /// Compute the effective fragment size assuming it is laid out at the given 921 /// \p SectionAddress and \p FragmentOffset. 922 uint64_t computeFragmentSize(const MCAsmLayout &Layout, 923 const MCFragment &F) const; 924 925 /// Find the symbol which defines the atom containing the given symbol, or 926 /// null if there is no such symbol. 927 const MCSymbolData *getAtom(const MCSymbolData *Symbol) const; 928 929 /// Check whether a particular symbol is visible to the linker and is required 930 /// in the symbol table, or whether it can be discarded by the assembler. This 931 /// also effects whether the assembler treats the label as potentially 932 /// defining a separate atom. 933 bool isSymbolLinkerVisible(const MCSymbol &SD) const; 934 935 /// Emit the section contents using the given object writer. 936 void writeSectionData(const MCSectionData *Section, 937 const MCAsmLayout &Layout) const; 938 939 /// Check whether a given symbol has been flagged with .thumb_func. 940 bool isThumbFunc(const MCSymbol *Func) const { 941 return ThumbFuncs.count(Func); 942 } 943 944 /// Flag a function symbol as the target of a .thumb_func directive. 945 void setIsThumbFunc(const MCSymbol *Func) { ThumbFuncs.insert(Func); } 946 947public: 948 /// Construct a new assembler instance. 949 /// 950 /// \param OS The stream to output to. 951 // 952 // FIXME: How are we going to parameterize this? Two obvious options are stay 953 // concrete and require clients to pass in a target like object. The other 954 // option is to make this abstract, and have targets provide concrete 955 // implementations as we do with AsmParser. 956 MCAssembler(MCContext &Context_, MCAsmBackend &Backend_, 957 MCCodeEmitter &Emitter_, MCObjectWriter &Writer_, 958 raw_ostream &OS); 959 ~MCAssembler(); 960 961 /// Reuse an assembler instance 962 /// 963 void reset(); 964 965 MCContext &getContext() const { return Context; } 966 967 MCAsmBackend &getBackend() const { return Backend; } 968 969 MCCodeEmitter &getEmitter() const { return Emitter; } 970 971 MCObjectWriter &getWriter() const { return Writer; } 972 973 /// Finish - Do final processing and write the object to the output stream. 974 /// \p Writer is used for custom object writer (as the MCJIT does), 975 /// if not specified it is automatically created from backend. 976 void Finish(); 977 978 // FIXME: This does not belong here. 979 bool getSubsectionsViaSymbols() const { 980 return SubsectionsViaSymbols; 981 } 982 void setSubsectionsViaSymbols(bool Value) { 983 SubsectionsViaSymbols = Value; 984 } 985 986 bool getRelaxAll() const { return RelaxAll; } 987 void setRelaxAll(bool Value) { RelaxAll = Value; } 988 989 bool getNoExecStack() const { return NoExecStack; } 990 void setNoExecStack(bool Value) { NoExecStack = Value; } 991 992 bool isBundlingEnabled() const { 993 return BundleAlignSize != 0; 994 } 995 996 unsigned getBundleAlignSize() const { 997 return BundleAlignSize; 998 } 999 1000 void setBundleAlignSize(unsigned Size) { 1001 assert((Size == 0 || !(Size & (Size - 1))) && 1002 "Expect a power-of-two bundle align size"); 1003 BundleAlignSize = Size; 1004 } 1005 1006 /// @name Section List Access 1007 /// @{ 1008 1009 const SectionDataListType &getSectionList() const { return Sections; } 1010 SectionDataListType &getSectionList() { return Sections; } 1011 1012 iterator begin() { return Sections.begin(); } 1013 const_iterator begin() const { return Sections.begin(); } 1014 1015 iterator end() { return Sections.end(); } 1016 const_iterator end() const { return Sections.end(); } 1017 1018 size_t size() const { return Sections.size(); } 1019 1020 /// @} 1021 /// @name Symbol List Access 1022 /// @{ 1023 1024 const SymbolDataListType &getSymbolList() const { return Symbols; } 1025 SymbolDataListType &getSymbolList() { return Symbols; } 1026 1027 symbol_iterator symbol_begin() { return Symbols.begin(); } 1028 const_symbol_iterator symbol_begin() const { return Symbols.begin(); } 1029 1030 symbol_iterator symbol_end() { return Symbols.end(); } 1031 const_symbol_iterator symbol_end() const { return Symbols.end(); } 1032 1033 size_t symbol_size() const { return Symbols.size(); } 1034 1035 /// @} 1036 /// @name Indirect Symbol List Access 1037 /// @{ 1038 1039 // FIXME: This is a total hack, this should not be here. Once things are 1040 // factored so that the streamer has direct access to the .o writer, it can 1041 // disappear. 1042 std::vector<IndirectSymbolData> &getIndirectSymbols() { 1043 return IndirectSymbols; 1044 } 1045 1046 indirect_symbol_iterator indirect_symbol_begin() { 1047 return IndirectSymbols.begin(); 1048 } 1049 const_indirect_symbol_iterator indirect_symbol_begin() const { 1050 return IndirectSymbols.begin(); 1051 } 1052 1053 indirect_symbol_iterator indirect_symbol_end() { 1054 return IndirectSymbols.end(); 1055 } 1056 const_indirect_symbol_iterator indirect_symbol_end() const { 1057 return IndirectSymbols.end(); 1058 } 1059 1060 size_t indirect_symbol_size() const { return IndirectSymbols.size(); } 1061 1062 /// @} 1063 /// @name Data Region List Access 1064 /// @{ 1065 1066 // FIXME: This is a total hack, this should not be here. Once things are 1067 // factored so that the streamer has direct access to the .o writer, it can 1068 // disappear. 1069 std::vector<DataRegionData> &getDataRegions() { 1070 return DataRegions; 1071 } 1072 1073 data_region_iterator data_region_begin() { 1074 return DataRegions.begin(); 1075 } 1076 const_data_region_iterator data_region_begin() const { 1077 return DataRegions.begin(); 1078 } 1079 1080 data_region_iterator data_region_end() { 1081 return DataRegions.end(); 1082 } 1083 const_data_region_iterator data_region_end() const { 1084 return DataRegions.end(); 1085 } 1086 1087 size_t data_region_size() const { return DataRegions.size(); } 1088 1089 /// @} 1090 /// @name Backend Data Access 1091 /// @{ 1092 1093 MCSectionData &getSectionData(const MCSection &Section) const { 1094 MCSectionData *Entry = SectionMap.lookup(&Section); 1095 assert(Entry && "Missing section data!"); 1096 return *Entry; 1097 } 1098 1099 MCSectionData &getOrCreateSectionData(const MCSection &Section, 1100 bool *Created = 0) { 1101 MCSectionData *&Entry = SectionMap[&Section]; 1102 1103 if (Created) *Created = !Entry; 1104 if (!Entry) 1105 Entry = new MCSectionData(Section, this); 1106 1107 return *Entry; 1108 } 1109 1110 MCSymbolData &getSymbolData(const MCSymbol &Symbol) const { 1111 MCSymbolData *Entry = SymbolMap.lookup(&Symbol); 1112 assert(Entry && "Missing symbol data!"); 1113 return *Entry; 1114 } 1115 1116 MCSymbolData &getOrCreateSymbolData(const MCSymbol &Symbol, 1117 bool *Created = 0) { 1118 MCSymbolData *&Entry = SymbolMap[&Symbol]; 1119 1120 if (Created) *Created = !Entry; 1121 if (!Entry) 1122 Entry = new MCSymbolData(Symbol, 0, 0, this); 1123 1124 return *Entry; 1125 } 1126 1127 /// @} 1128 1129 void dump(); 1130}; 1131 1132} // end namespace llvm 1133 1134#endif 1135