MCContext.cpp 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492
  1. //===- lib/MC/MCContext.cpp - Machine Code Context ------------------------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. #include "llvm/MC/MCContext.h"
  10. #include "llvm/ADT/SmallString.h"
  11. #include "llvm/ADT/Twine.h"
  12. #include "llvm/MC/MCAssembler.h"
  13. #include "llvm/MC/MCAsmInfo.h"
  14. #include "llvm/MC/MCDwarf.h"
  15. #include "llvm/MC/MCLabel.h"
  16. #include "llvm/MC/MCObjectFileInfo.h"
  17. #include "llvm/MC/MCRegisterInfo.h"
  18. #include "llvm/MC/MCSectionCOFF.h"
  19. #include "llvm/MC/MCSectionELF.h"
  20. #include "llvm/MC/MCSectionMachO.h"
  21. #include "llvm/MC/MCStreamer.h"
  22. #include "llvm/MC/MCSymbolCOFF.h"
  23. #include "llvm/MC/MCSymbolELF.h"
  24. #include "llvm/MC/MCSymbolMachO.h"
  25. #include "llvm/Support/ELF.h"
  26. #include "llvm/Support/ErrorHandling.h"
  27. #include "llvm/Support/FileSystem.h"
  28. #include "llvm/Support/MemoryBuffer.h"
  29. #include "llvm/Support/Signals.h"
  30. #include "llvm/Support/SourceMgr.h"
  31. #include <map>
  32. using namespace llvm;
  33. MCContext::MCContext(const MCAsmInfo *mai, const MCRegisterInfo *mri,
  34. const MCObjectFileInfo *mofi, const SourceMgr *mgr,
  35. bool DoAutoReset)
  36. : SrcMgr(mgr), MAI(mai), MRI(mri), MOFI(mofi), Allocator(),
  37. Symbols(Allocator), UsedNames(Allocator),
  38. CurrentDwarfLoc(0, 0, 0, DWARF2_FLAG_IS_STMT, 0, 0), DwarfLocSeen(false),
  39. GenDwarfForAssembly(false), GenDwarfFileNumber(0), DwarfVersion(4),
  40. AllowTemporaryLabels(true), DwarfCompileUnitID(0),
  41. AutoReset(DoAutoReset) {
  42. std::error_code EC = llvm::sys::fs::current_path(CompilationDir);
  43. if (EC)
  44. CompilationDir.clear();
  45. SecureLogFile = getenv("AS_SECURE_LOG_FILE");
  46. SecureLog = nullptr;
  47. SecureLogUsed = false;
  48. if (SrcMgr && SrcMgr->getNumBuffers())
  49. MainFileName =
  50. SrcMgr->getMemoryBuffer(SrcMgr->getMainFileID())->getBufferIdentifier();
  51. }
  52. MCContext::~MCContext() {
  53. if (AutoReset)
  54. reset();
  55. // NOTE: The symbols are all allocated out of a bump pointer allocator,
  56. // we don't need to free them here.
  57. // If the stream for the .secure_log_unique directive was created free it.
  58. delete (raw_ostream *)SecureLog;
  59. }
  60. //===----------------------------------------------------------------------===//
  61. // Module Lifetime Management
  62. //===----------------------------------------------------------------------===//
  63. void MCContext::reset() {
  64. // Call the destructors so the fragments are freed
  65. for (auto &I : ELFUniquingMap)
  66. I.second->~MCSectionELF();
  67. for (auto &I : COFFUniquingMap)
  68. I.second->~MCSectionCOFF();
  69. for (auto &I : MachOUniquingMap)
  70. I.second->~MCSectionMachO();
  71. UsedNames.clear();
  72. Symbols.clear();
  73. Allocator.Reset();
  74. Instances.clear();
  75. CompilationDir.clear();
  76. MainFileName.clear();
  77. MCDwarfLineTablesCUMap.clear();
  78. SectionsForRanges.clear();
  79. MCGenDwarfLabelEntries.clear();
  80. DwarfDebugFlags = StringRef();
  81. DwarfCompileUnitID = 0;
  82. CurrentDwarfLoc = MCDwarfLoc(0, 0, 0, DWARF2_FLAG_IS_STMT, 0, 0);
  83. MachOUniquingMap.clear();
  84. ELFUniquingMap.clear();
  85. COFFUniquingMap.clear();
  86. NextID.clear();
  87. AllowTemporaryLabels = true;
  88. DwarfLocSeen = false;
  89. GenDwarfForAssembly = false;
  90. GenDwarfFileNumber = 0;
  91. }
  92. //===----------------------------------------------------------------------===//
  93. // Symbol Manipulation
  94. //===----------------------------------------------------------------------===//
  95. MCSymbol *MCContext::getOrCreateSymbol(const Twine &Name) {
  96. SmallString<128> NameSV;
  97. StringRef NameRef = Name.toStringRef(NameSV);
  98. assert(!NameRef.empty() && "Normal symbols cannot be unnamed!");
  99. MCSymbol *&Sym = Symbols[NameRef];
  100. if (!Sym)
  101. Sym = createSymbol(NameRef, false, false);
  102. return Sym;
  103. }
  104. MCSymbolELF *MCContext::getOrCreateSectionSymbol(const MCSectionELF &Section) {
  105. MCSymbolELF *&Sym = SectionSymbols[&Section];
  106. if (Sym)
  107. return Sym;
  108. StringRef Name = Section.getSectionName();
  109. MCSymbol *&OldSym = Symbols[Name];
  110. if (OldSym && OldSym->isUndefined()) {
  111. Sym = cast<MCSymbolELF>(OldSym);
  112. return Sym;
  113. }
  114. auto NameIter = UsedNames.insert(std::make_pair(Name, true)).first;
  115. Sym = new (&*NameIter, *this) MCSymbolELF(&*NameIter, /*isTemporary*/ false);
  116. if (!OldSym)
  117. OldSym = Sym;
  118. return Sym;
  119. }
  120. MCSymbol *MCContext::getOrCreateFrameAllocSymbol(StringRef FuncName,
  121. unsigned Idx) {
  122. return getOrCreateSymbol(Twine(MAI->getPrivateGlobalPrefix()) + FuncName +
  123. "$frame_escape_" + Twine(Idx));
  124. }
  125. MCSymbol *MCContext::getOrCreateParentFrameOffsetSymbol(StringRef FuncName) {
  126. return getOrCreateSymbol(Twine(MAI->getPrivateGlobalPrefix()) + FuncName +
  127. "$parent_frame_offset");
  128. }
  129. MCSymbol *MCContext::getOrCreateLSDASymbol(StringRef FuncName) {
  130. return getOrCreateSymbol(Twine(MAI->getPrivateGlobalPrefix()) + "__ehtable$" +
  131. FuncName);
  132. }
  133. MCSymbol *MCContext::createSymbolImpl(const StringMapEntry<bool> *Name,
  134. bool IsTemporary) {
  135. if (MOFI) {
  136. switch (MOFI->getObjectFileType()) {
  137. case MCObjectFileInfo::IsCOFF:
  138. return new (Name, *this) MCSymbolCOFF(Name, IsTemporary);
  139. case MCObjectFileInfo::IsELF:
  140. return new (Name, *this) MCSymbolELF(Name, IsTemporary);
  141. case MCObjectFileInfo::IsMachO:
  142. return new (Name, *this) MCSymbolMachO(Name, IsTemporary);
  143. }
  144. }
  145. return new (Name, *this) MCSymbol(MCSymbol::SymbolKindUnset, Name,
  146. IsTemporary);
  147. }
  148. MCSymbol *MCContext::createSymbol(StringRef Name, bool AlwaysAddSuffix,
  149. bool CanBeUnnamed) {
  150. if (CanBeUnnamed && !UseNamesOnTempLabels)
  151. return createSymbolImpl(nullptr, true);
  152. // Determine whether this is an user writter assembler temporary or normal
  153. // label, if used.
  154. bool IsTemporary = CanBeUnnamed;
  155. if (AllowTemporaryLabels && !IsTemporary)
  156. IsTemporary = Name.startswith(MAI->getPrivateGlobalPrefix());
  157. SmallString<128> NewName = Name;
  158. bool AddSuffix = AlwaysAddSuffix;
  159. unsigned &NextUniqueID = NextID[Name];
  160. for (;;) {
  161. if (AddSuffix) {
  162. NewName.resize(Name.size());
  163. raw_svector_ostream(NewName) << NextUniqueID++;
  164. }
  165. auto NameEntry = UsedNames.insert(std::make_pair(NewName, true));
  166. if (NameEntry.second) {
  167. // Ok, we found a name. Have the MCSymbol object itself refer to the copy
  168. // of the string that is embedded in the UsedNames entry.
  169. return createSymbolImpl(&*NameEntry.first, IsTemporary);
  170. }
  171. assert(IsTemporary && "Cannot rename non-temporary symbols");
  172. AddSuffix = true;
  173. }
  174. llvm_unreachable("Infinite loop");
  175. }
  176. MCSymbol *MCContext::createTempSymbol(const Twine &Name, bool AlwaysAddSuffix,
  177. bool CanBeUnnamed) {
  178. SmallString<128> NameSV;
  179. raw_svector_ostream(NameSV) << MAI->getPrivateGlobalPrefix() << Name;
  180. return createSymbol(NameSV, AlwaysAddSuffix, CanBeUnnamed);
  181. }
  182. MCSymbol *MCContext::createLinkerPrivateTempSymbol() {
  183. SmallString<128> NameSV;
  184. raw_svector_ostream(NameSV) << MAI->getLinkerPrivateGlobalPrefix() << "tmp";
  185. return createSymbol(NameSV, true, false);
  186. }
  187. MCSymbol *MCContext::createTempSymbol(bool CanBeUnnamed) {
  188. return createTempSymbol("tmp", true, CanBeUnnamed);
  189. }
  190. unsigned MCContext::NextInstance(unsigned LocalLabelVal) {
  191. MCLabel *&Label = Instances[LocalLabelVal];
  192. if (!Label)
  193. Label = new (*this) MCLabel(0);
  194. return Label->incInstance();
  195. }
  196. unsigned MCContext::GetInstance(unsigned LocalLabelVal) {
  197. MCLabel *&Label = Instances[LocalLabelVal];
  198. if (!Label)
  199. Label = new (*this) MCLabel(0);
  200. return Label->getInstance();
  201. }
  202. MCSymbol *MCContext::getOrCreateDirectionalLocalSymbol(unsigned LocalLabelVal,
  203. unsigned Instance) {
  204. MCSymbol *&Sym = LocalSymbols[std::make_pair(LocalLabelVal, Instance)];
  205. if (!Sym)
  206. Sym = createTempSymbol(false);
  207. return Sym;
  208. }
  209. MCSymbol *MCContext::createDirectionalLocalSymbol(unsigned LocalLabelVal) {
  210. unsigned Instance = NextInstance(LocalLabelVal);
  211. return getOrCreateDirectionalLocalSymbol(LocalLabelVal, Instance);
  212. }
  213. MCSymbol *MCContext::getDirectionalLocalSymbol(unsigned LocalLabelVal,
  214. bool Before) {
  215. unsigned Instance = GetInstance(LocalLabelVal);
  216. if (!Before)
  217. ++Instance;
  218. return getOrCreateDirectionalLocalSymbol(LocalLabelVal, Instance);
  219. }
  220. MCSymbol *MCContext::lookupSymbol(const Twine &Name) const {
  221. SmallString<128> NameSV;
  222. StringRef NameRef = Name.toStringRef(NameSV);
  223. return Symbols.lookup(NameRef);
  224. }
  225. //===----------------------------------------------------------------------===//
  226. // Section Management
  227. //===----------------------------------------------------------------------===//
  228. MCSectionMachO *MCContext::getMachOSection(StringRef Segment, StringRef Section,
  229. unsigned TypeAndAttributes,
  230. unsigned Reserved2, SectionKind Kind,
  231. const char *BeginSymName) {
  232. // We unique sections by their segment/section pair. The returned section
  233. // may not have the same flags as the requested section, if so this should be
  234. // diagnosed by the client as an error.
  235. // Form the name to look up.
  236. SmallString<64> Name;
  237. Name += Segment;
  238. Name.push_back(',');
  239. Name += Section;
  240. // Do the lookup, if we have a hit, return it.
  241. MCSectionMachO *&Entry = MachOUniquingMap[Name];
  242. if (Entry)
  243. return Entry;
  244. MCSymbol *Begin = nullptr;
  245. if (BeginSymName)
  246. Begin = createTempSymbol(BeginSymName, false);
  247. // Otherwise, return a new section.
  248. return Entry = new (*this) MCSectionMachO(Segment, Section, TypeAndAttributes,
  249. Reserved2, Kind, Begin);
  250. }
  251. void MCContext::renameELFSection(MCSectionELF *Section, StringRef Name) {
  252. StringRef GroupName;
  253. if (const MCSymbol *Group = Section->getGroup())
  254. GroupName = Group->getName();
  255. unsigned UniqueID = Section->getUniqueID();
  256. ELFUniquingMap.erase(
  257. ELFSectionKey{Section->getSectionName(), GroupName, UniqueID});
  258. auto I = ELFUniquingMap.insert(std::make_pair(
  259. ELFSectionKey{Name, GroupName, UniqueID},
  260. Section))
  261. .first;
  262. StringRef CachedName = I->first.SectionName;
  263. const_cast<MCSectionELF *>(Section)->setSectionName(CachedName);
  264. }
  265. MCSectionELF *MCContext::createELFRelSection(StringRef Name, unsigned Type,
  266. unsigned Flags, unsigned EntrySize,
  267. const MCSymbolELF *Group,
  268. const MCSectionELF *Associated) {
  269. StringMap<bool>::iterator I;
  270. bool Inserted;
  271. std::tie(I, Inserted) = ELFRelSecNames.insert(std::make_pair(Name, true));
  272. return new (*this)
  273. MCSectionELF(I->getKey(), Type, Flags, SectionKind::getReadOnly(),
  274. EntrySize, Group, true, nullptr, Associated);
  275. }
  276. MCSectionELF *MCContext::getELFSection(StringRef Section, unsigned Type,
  277. unsigned Flags, unsigned EntrySize,
  278. StringRef Group, unsigned UniqueID,
  279. const char *BeginSymName) {
  280. MCSymbolELF *GroupSym = nullptr;
  281. if (!Group.empty())
  282. GroupSym = cast<MCSymbolELF>(getOrCreateSymbol(Group));
  283. return getELFSection(Section, Type, Flags, EntrySize, GroupSym, UniqueID,
  284. BeginSymName, nullptr);
  285. }
  286. MCSectionELF *MCContext::getELFSection(StringRef Section, unsigned Type,
  287. unsigned Flags, unsigned EntrySize,
  288. const MCSymbolELF *GroupSym,
  289. unsigned UniqueID,
  290. const char *BeginSymName,
  291. const MCSectionELF *Associated) {
  292. StringRef Group = "";
  293. if (GroupSym)
  294. Group = GroupSym->getName();
  295. // Do the lookup, if we have a hit, return it.
  296. auto IterBool = ELFUniquingMap.insert(
  297. std::make_pair(ELFSectionKey{Section, Group, UniqueID}, nullptr));
  298. auto &Entry = *IterBool.first;
  299. if (!IterBool.second)
  300. return Entry.second;
  301. StringRef CachedName = Entry.first.SectionName;
  302. SectionKind Kind;
  303. if (Flags & ELF::SHF_EXECINSTR)
  304. Kind = SectionKind::getText();
  305. else
  306. Kind = SectionKind::getReadOnly();
  307. MCSymbol *Begin = nullptr;
  308. if (BeginSymName)
  309. Begin = createTempSymbol(BeginSymName, false);
  310. MCSectionELF *Result =
  311. new (*this) MCSectionELF(CachedName, Type, Flags, Kind, EntrySize,
  312. GroupSym, UniqueID, Begin, Associated);
  313. Entry.second = Result;
  314. return Result;
  315. }
  316. MCSectionELF *MCContext::createELFGroupSection(const MCSymbolELF *Group) {
  317. MCSectionELF *Result = new (*this)
  318. MCSectionELF(".group", ELF::SHT_GROUP, 0, SectionKind::getReadOnly(), 4,
  319. Group, ~0, nullptr, nullptr);
  320. return Result;
  321. }
  322. MCSectionCOFF *MCContext::getCOFFSection(StringRef Section,
  323. unsigned Characteristics,
  324. SectionKind Kind,
  325. StringRef COMDATSymName, int Selection,
  326. const char *BeginSymName) {
  327. MCSymbol *COMDATSymbol = nullptr;
  328. if (!COMDATSymName.empty()) {
  329. COMDATSymbol = getOrCreateSymbol(COMDATSymName);
  330. COMDATSymName = COMDATSymbol->getName();
  331. }
  332. // Do the lookup, if we have a hit, return it.
  333. COFFSectionKey T{Section, COMDATSymName, Selection};
  334. auto IterBool = COFFUniquingMap.insert(std::make_pair(T, nullptr));
  335. auto Iter = IterBool.first;
  336. if (!IterBool.second)
  337. return Iter->second;
  338. MCSymbol *Begin = nullptr;
  339. if (BeginSymName)
  340. Begin = createTempSymbol(BeginSymName, false);
  341. StringRef CachedName = Iter->first.SectionName;
  342. MCSectionCOFF *Result = new (*this) MCSectionCOFF(
  343. CachedName, Characteristics, COMDATSymbol, Selection, Kind, Begin);
  344. Iter->second = Result;
  345. return Result;
  346. }
  347. MCSectionCOFF *MCContext::getCOFFSection(StringRef Section,
  348. unsigned Characteristics,
  349. SectionKind Kind,
  350. const char *BeginSymName) {
  351. return getCOFFSection(Section, Characteristics, Kind, "", 0, BeginSymName);
  352. }
  353. MCSectionCOFF *MCContext::getCOFFSection(StringRef Section) {
  354. COFFSectionKey T{Section, "", 0};
  355. auto Iter = COFFUniquingMap.find(T);
  356. if (Iter == COFFUniquingMap.end())
  357. return nullptr;
  358. return Iter->second;
  359. }
  360. MCSectionCOFF *MCContext::getAssociativeCOFFSection(MCSectionCOFF *Sec,
  361. const MCSymbol *KeySym) {
  362. // Return the normal section if we don't have to be associative.
  363. if (!KeySym)
  364. return Sec;
  365. // Make an associative section with the same name and kind as the normal
  366. // section.
  367. unsigned Characteristics =
  368. Sec->getCharacteristics() | COFF::IMAGE_SCN_LNK_COMDAT;
  369. return getCOFFSection(Sec->getSectionName(), Characteristics, Sec->getKind(),
  370. KeySym->getName(),
  371. COFF::IMAGE_COMDAT_SELECT_ASSOCIATIVE);
  372. }
  373. //===----------------------------------------------------------------------===//
  374. // Dwarf Management
  375. //===----------------------------------------------------------------------===//
  376. /// getDwarfFile - takes a file name an number to place in the dwarf file and
  377. /// directory tables. If the file number has already been allocated it is an
  378. /// error and zero is returned and the client reports the error, else the
  379. /// allocated file number is returned. The file numbers may be in any order.
  380. unsigned MCContext::getDwarfFile(StringRef Directory, StringRef FileName,
  381. unsigned FileNumber, unsigned CUID) {
  382. MCDwarfLineTable &Table = MCDwarfLineTablesCUMap[CUID];
  383. return Table.getFile(Directory, FileName, FileNumber);
  384. }
  385. /// isValidDwarfFileNumber - takes a dwarf file number and returns true if it
  386. /// currently is assigned and false otherwise.
  387. bool MCContext::isValidDwarfFileNumber(unsigned FileNumber, unsigned CUID) {
  388. const SmallVectorImpl<MCDwarfFile> &MCDwarfFiles = getMCDwarfFiles(CUID);
  389. if (FileNumber == 0 || FileNumber >= MCDwarfFiles.size())
  390. return false;
  391. return !MCDwarfFiles[FileNumber].Name.empty();
  392. }
  393. /// Remove empty sections from SectionStartEndSyms, to avoid generating
  394. /// useless debug info for them.
  395. void MCContext::finalizeDwarfSections(MCStreamer &MCOS) {
  396. SectionsForRanges.remove_if(
  397. [&](MCSection *Sec) { return !MCOS.mayHaveInstructions(*Sec); });
  398. }
  399. void MCContext::reportFatalError(SMLoc Loc, const Twine &Msg) const {
  400. #if 0 // HLSL Change - analysis shows this isn't called on corruption but on paths with no recovery; unwind instead of terminating
  401. // If we have a source manager and a location, use it. Otherwise just
  402. // use the generic report_fatal_error().
  403. if (!SrcMgr || Loc == SMLoc())
  404. report_fatal_error(Msg, false);
  405. // Use the source manager to print the message.
  406. SrcMgr->PrintMessage(Loc, SourceMgr::DK_Error, Msg);
  407. // If we reached here, we are failing ungracefully. Run the interrupt handlers
  408. // to make sure any special cleanups get done, in particular that we remove
  409. // files registered with RemoveFileOnSignal.
  410. sys::RunInterruptHandlers();
  411. exit(1);
  412. #else
  413. throw std::exception();
  414. #endif
  415. }