xref: /freebsd-src/contrib/llvm-project/llvm/lib/Target/NVPTX/MCTargetDesc/NVPTXTargetStreamer.cpp (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
10b57cec5SDimitry Andric //=====- NVPTXTargetStreamer.cpp - NVPTXTargetStreamer class ------------=====//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric //
90b57cec5SDimitry Andric // This file implements the NVPTXTargetStreamer class.
100b57cec5SDimitry Andric //
110b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
120b57cec5SDimitry Andric 
130b57cec5SDimitry Andric #include "NVPTXTargetStreamer.h"
140b57cec5SDimitry Andric #include "llvm/MC/MCAsmInfo.h"
150b57cec5SDimitry Andric #include "llvm/MC/MCContext.h"
160b57cec5SDimitry Andric #include "llvm/MC/MCObjectFileInfo.h"
170b57cec5SDimitry Andric 
180b57cec5SDimitry Andric using namespace llvm;
190b57cec5SDimitry Andric 
200b57cec5SDimitry Andric //
210b57cec5SDimitry Andric // NVPTXTargetStreamer Implemenation
220b57cec5SDimitry Andric //
230b57cec5SDimitry Andric NVPTXTargetStreamer::NVPTXTargetStreamer(MCStreamer &S) : MCTargetStreamer(S) {}
240b57cec5SDimitry Andric NVPTXTargetStreamer::~NVPTXTargetStreamer() = default;
250b57cec5SDimitry Andric 
26bdd1243dSDimitry Andric NVPTXAsmTargetStreamer::NVPTXAsmTargetStreamer(MCStreamer &S)
27bdd1243dSDimitry Andric     : NVPTXTargetStreamer(S) {}
28bdd1243dSDimitry Andric NVPTXAsmTargetStreamer::~NVPTXAsmTargetStreamer() = default;
29bdd1243dSDimitry Andric 
300b57cec5SDimitry Andric void NVPTXTargetStreamer::outputDwarfFileDirectives() {
310b57cec5SDimitry Andric   for (const std::string &S : DwarfFiles)
32349cc55cSDimitry Andric     getStreamer().emitRawText(S);
330b57cec5SDimitry Andric   DwarfFiles.clear();
340b57cec5SDimitry Andric }
350b57cec5SDimitry Andric 
360b57cec5SDimitry Andric void NVPTXTargetStreamer::closeLastSection() {
370b57cec5SDimitry Andric   if (HasSections)
385ffd83dbSDimitry Andric     getStreamer().emitRawText("\t}");
390b57cec5SDimitry Andric }
400b57cec5SDimitry Andric 
410b57cec5SDimitry Andric void NVPTXTargetStreamer::emitDwarfFileDirective(StringRef Directive) {
420b57cec5SDimitry Andric   DwarfFiles.emplace_back(Directive);
430b57cec5SDimitry Andric }
440b57cec5SDimitry Andric 
450b57cec5SDimitry Andric static bool isDwarfSection(const MCObjectFileInfo *FI,
460b57cec5SDimitry Andric                            const MCSection *Section) {
470b57cec5SDimitry Andric   // FIXME: the checks for the DWARF sections are very fragile and should be
480b57cec5SDimitry Andric   // fixed up in a followup patch.
49*0fca6ea1SDimitry Andric   if (!Section || Section->isText())
500b57cec5SDimitry Andric     return false;
510b57cec5SDimitry Andric   return Section == FI->getDwarfAbbrevSection() ||
520b57cec5SDimitry Andric          Section == FI->getDwarfInfoSection() ||
530b57cec5SDimitry Andric          Section == FI->getDwarfMacinfoSection() ||
540b57cec5SDimitry Andric          Section == FI->getDwarfFrameSection() ||
550b57cec5SDimitry Andric          Section == FI->getDwarfAddrSection() ||
560b57cec5SDimitry Andric          Section == FI->getDwarfRangesSection() ||
570b57cec5SDimitry Andric          Section == FI->getDwarfARangesSection() ||
580b57cec5SDimitry Andric          Section == FI->getDwarfLocSection() ||
590b57cec5SDimitry Andric          Section == FI->getDwarfStrSection() ||
600b57cec5SDimitry Andric          Section == FI->getDwarfLineSection() ||
610b57cec5SDimitry Andric          Section == FI->getDwarfStrOffSection() ||
620b57cec5SDimitry Andric          Section == FI->getDwarfLineStrSection() ||
630b57cec5SDimitry Andric          Section == FI->getDwarfPubNamesSection() ||
640b57cec5SDimitry Andric          Section == FI->getDwarfPubTypesSection() ||
650b57cec5SDimitry Andric          Section == FI->getDwarfSwiftASTSection() ||
660b57cec5SDimitry Andric          Section == FI->getDwarfTypesDWOSection() ||
670b57cec5SDimitry Andric          Section == FI->getDwarfAbbrevDWOSection() ||
680b57cec5SDimitry Andric          Section == FI->getDwarfAccelObjCSection() ||
690b57cec5SDimitry Andric          Section == FI->getDwarfAccelNamesSection() ||
700b57cec5SDimitry Andric          Section == FI->getDwarfAccelTypesSection() ||
710b57cec5SDimitry Andric          Section == FI->getDwarfAccelNamespaceSection() ||
720b57cec5SDimitry Andric          Section == FI->getDwarfLocDWOSection() ||
730b57cec5SDimitry Andric          Section == FI->getDwarfStrDWOSection() ||
740b57cec5SDimitry Andric          Section == FI->getDwarfCUIndexSection() ||
750b57cec5SDimitry Andric          Section == FI->getDwarfInfoDWOSection() ||
760b57cec5SDimitry Andric          Section == FI->getDwarfLineDWOSection() ||
770b57cec5SDimitry Andric          Section == FI->getDwarfTUIndexSection() ||
780b57cec5SDimitry Andric          Section == FI->getDwarfStrOffDWOSection() ||
790b57cec5SDimitry Andric          Section == FI->getDwarfDebugNamesSection() ||
800b57cec5SDimitry Andric          Section == FI->getDwarfDebugInlineSection() ||
810b57cec5SDimitry Andric          Section == FI->getDwarfGnuPubNamesSection() ||
820b57cec5SDimitry Andric          Section == FI->getDwarfGnuPubTypesSection();
830b57cec5SDimitry Andric }
840b57cec5SDimitry Andric 
850b57cec5SDimitry Andric void NVPTXTargetStreamer::changeSection(const MCSection *CurSection,
86*0fca6ea1SDimitry Andric                                         MCSection *Section, uint32_t SubSection,
870b57cec5SDimitry Andric                                         raw_ostream &OS) {
880b57cec5SDimitry Andric   assert(!SubSection && "SubSection is not null!");
890b57cec5SDimitry Andric   const MCObjectFileInfo *FI = getStreamer().getContext().getObjectFileInfo();
900b57cec5SDimitry Andric   // Emit closing brace for DWARF sections only.
910b57cec5SDimitry Andric   if (isDwarfSection(FI, CurSection))
920b57cec5SDimitry Andric     OS << "\t}\n";
930b57cec5SDimitry Andric   if (isDwarfSection(FI, Section)) {
940b57cec5SDimitry Andric     // Emit DWARF .file directives in the outermost scope.
950b57cec5SDimitry Andric     outputDwarfFileDirectives();
960b57cec5SDimitry Andric     OS << "\t.section";
9781ad6265SDimitry Andric     Section->printSwitchToSection(*getStreamer().getContext().getAsmInfo(),
98fe6060f1SDimitry Andric                                   getStreamer().getContext().getTargetTriple(),
99fe6060f1SDimitry Andric                                   OS, SubSection);
1000b57cec5SDimitry Andric     // DWARF sections are enclosed into braces - emit the open one.
1010b57cec5SDimitry Andric     OS << "\t{\n";
1020b57cec5SDimitry Andric     HasSections = true;
1030b57cec5SDimitry Andric   }
1040b57cec5SDimitry Andric }
1050b57cec5SDimitry Andric 
1060b57cec5SDimitry Andric void NVPTXTargetStreamer::emitRawBytes(StringRef Data) {
1070b57cec5SDimitry Andric   MCTargetStreamer::emitRawBytes(Data);
1080b57cec5SDimitry Andric   // TODO: enable this once the bug in the ptxas with the packed bytes is
1090b57cec5SDimitry Andric   // resolved. Currently, (it is confirmed by NVidia) it causes a crash in
1100b57cec5SDimitry Andric   // ptxas.
1110b57cec5SDimitry Andric #if 0
1120b57cec5SDimitry Andric   const MCAsmInfo *MAI = Streamer.getContext().getAsmInfo();
1130b57cec5SDimitry Andric   const char *Directive = MAI->getData8bitsDirective();
1140b57cec5SDimitry Andric   unsigned NumElements = Data.size();
1150b57cec5SDimitry Andric   const unsigned MaxLen = 40;
1160b57cec5SDimitry Andric   unsigned NumChunks = 1 + ((NumElements - 1) / MaxLen);
1170b57cec5SDimitry Andric   // Split the very long directives into several parts if the limit is
1180b57cec5SDimitry Andric   // specified.
1190b57cec5SDimitry Andric   for (unsigned I = 0; I < NumChunks; ++I) {
1200b57cec5SDimitry Andric     SmallString<128> Str;
1210b57cec5SDimitry Andric     raw_svector_ostream OS(Str);
1220b57cec5SDimitry Andric 
1230b57cec5SDimitry Andric     const char *Label = Directive;
1240b57cec5SDimitry Andric     for (auto It = std::next(Data.bytes_begin(), I * MaxLen),
1250b57cec5SDimitry Andric               End = (I == NumChunks - 1)
1260b57cec5SDimitry Andric                         ? Data.bytes_end()
1270b57cec5SDimitry Andric                         : std::next(Data.bytes_begin(), (I + 1) * MaxLen);
1280b57cec5SDimitry Andric          It != End; ++It) {
1290b57cec5SDimitry Andric       OS << Label << (unsigned)*It;
1300b57cec5SDimitry Andric       if (Label == Directive)
1310b57cec5SDimitry Andric         Label = ",";
1320b57cec5SDimitry Andric     }
1335ffd83dbSDimitry Andric     Streamer.emitRawText(OS.str());
1340b57cec5SDimitry Andric   }
1350b57cec5SDimitry Andric #endif
1360b57cec5SDimitry Andric }
1370b57cec5SDimitry Andric 
138