diff options
Diffstat (limited to 'lib/Target')
52 files changed, 1409 insertions, 1230 deletions
diff --git a/lib/Target/ARM/ARMISelLowering.cpp b/lib/Target/ARM/ARMISelLowering.cpp index 226f1618c9..3b1be76424 100644 --- a/lib/Target/ARM/ARMISelLowering.cpp +++ b/lib/Target/ARM/ARMISelLowering.cpp @@ -34,6 +34,7 @@ #include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/CodeGen/PseudoSourceValue.h" #include "llvm/CodeGen/SelectionDAG.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Target/TargetOptions.h" #include "llvm/ADT/VectorExtras.h" #include "llvm/Support/ErrorHandling.h" @@ -103,8 +104,14 @@ void ARMTargetLowering::addQRTypeForNEON(MVT VT) { addTypeForNEON(VT, MVT::v2f64, MVT::v4i32); } +static TargetLoweringObjectFile *createTLOF(TargetMachine &TM) { + if (TM.getSubtarget<ARMSubtarget>().isTargetDarwin()) + return new TargetLoweringObjectFileMachO(); + return new TargetLoweringObjectFileELF(true); +} + ARMTargetLowering::ARMTargetLowering(TargetMachine &TM) - : TargetLowering(TM), ARMPCLabelIndex(0) { + : TargetLowering(TM, createTLOF(TM)), ARMPCLabelIndex(0) { Subtarget = &TM.getSubtarget<ARMSubtarget>(); if (Subtarget->isTargetDarwin()) { diff --git a/lib/Target/ARM/ARMTargetAsmInfo.cpp b/lib/Target/ARM/ARMTargetAsmInfo.cpp index 87f8a68564..34c187492f 100644 --- a/lib/Target/ARM/ARMTargetAsmInfo.cpp +++ b/lib/Target/ARM/ARMTargetAsmInfo.cpp @@ -59,8 +59,6 @@ ARMELFTargetAsmInfo::ARMELFTargetAsmInfo(const ARMBaseTargetMachine &TM): ARMTargetAsmInfo<ELFTargetAsmInfo>(TM) { Subtarget = &TM.getSubtarget<ARMSubtarget>(); - BSSSection_ = getOrCreateSection("\t.bss", true, SectionKind::BSS); - NeedsSet = false; HasLEB128 = true; AbsoluteDebugSectionOffsets = true; diff --git a/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp b/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp index 1154aaf714..d82b7585f2 100644 --- a/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp +++ b/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp @@ -29,6 +29,7 @@ #include "llvm/CodeGen/MachineJumpTableInfo.h" #include "llvm/Target/TargetAsmInfo.h" #include "llvm/Target/TargetData.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Target/TargetMachine.h" #include "llvm/Target/TargetOptions.h" #include "llvm/Target/TargetRegistry.h" @@ -1127,7 +1128,7 @@ void ARMAsmPrinter::PrintGlobalVariable(const GlobalVariable* GVar) { if (Subtarget->isTargetELF()) O << "\t.type " << name << ",%object\n"; - const Section *TheSection = TAI->SectionForGlobal(GVar); + const Section *TheSection = getObjFileLowering().SectionForGlobal(GVar, TM); SwitchToSection(TheSection); // FIXME: get this stuff from section kind flags. @@ -1154,7 +1155,7 @@ void ARMAsmPrinter::PrintGlobalVariable(const GlobalVariable* GVar) { O << TAI->getCOMMDirective() << name << "," << Size << ',' << Align; } else { - SwitchToSection(TAI->SectionForGlobal(GVar)); + SwitchToSection(getObjFileLowering().SectionForGlobal(GVar, TM)); O << "\t.globl " << name << '\n' << TAI->getWeakDefDirective() << name << '\n'; EmitAlignment(Align, GVar); @@ -1285,7 +1286,7 @@ bool ARMAsmPrinter::doFinalization(Module &M) { } if (!HiddenGVNonLazyPtrs.empty()) { - SwitchToSection(TAI->getDataSection()); + SwitchToSection(getObjFileLowering().getDataSection()); for (StringMap<std::string>::iterator I = HiddenGVNonLazyPtrs.begin(), E = HiddenGVNonLazyPtrs.end(); I != E; ++I) { EmitAlignment(2); diff --git a/lib/Target/Alpha/AlphaISelLowering.cpp b/lib/Target/Alpha/AlphaISelLowering.cpp index 310a4a6b03..f7a38c2a48 100644 --- a/lib/Target/Alpha/AlphaISelLowering.cpp +++ b/lib/Target/Alpha/AlphaISelLowering.cpp @@ -21,6 +21,7 @@ #include "llvm/CodeGen/SelectionDAG.h" #include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/CodeGen/PseudoSourceValue.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Constants.h" #include "llvm/Function.h" #include "llvm/Module.h" @@ -30,6 +31,17 @@ #include "llvm/Support/raw_ostream.h" using namespace llvm; + +class TargetLoweringObjectFileAlpha : public TargetLoweringObjectFile { +public: + TargetLoweringObjectFileAlpha() { + TextSection = getOrCreateSection("_text", true, SectionKind::Text); + DataSection = getOrCreateSection("_data", true, SectionKind::DataRel); + } +}; + + + /// AddLiveIn - This helper function adds the specified physical register to the /// MachineFunction as a live in value. It also creates a corresponding virtual /// register for it. @@ -41,7 +53,8 @@ static unsigned AddLiveIn(MachineFunction &MF, unsigned PReg, return VReg; } -AlphaTargetLowering::AlphaTargetLowering(TargetMachine &TM) : TargetLowering(TM) { +AlphaTargetLowering::AlphaTargetLowering(TargetMachine &TM) + : TargetLowering(TM, new TargetLoweringObjectFileAlpha()) { // Set up the TargetLowering object. //I am having problems with shr n i8 1 setShiftAmountType(MVT::i64); diff --git a/lib/Target/Alpha/AlphaTargetAsmInfo.cpp b/lib/Target/Alpha/AlphaTargetAsmInfo.cpp index 12fadfb542..6499552242 100644 --- a/lib/Target/Alpha/AlphaTargetAsmInfo.cpp +++ b/lib/Target/Alpha/AlphaTargetAsmInfo.cpp @@ -23,7 +23,4 @@ AlphaTargetAsmInfo::AlphaTargetAsmInfo(const AlphaTargetMachine &TM) JumpTableDirective = ".gprel32"; JumpTableDataSection = "\t.section .rodata\n"; WeakRefDirective = "\t.weak\t"; - - TextSection = getOrCreateSection("_text", true, SectionKind::Text); - DataSection = getOrCreateSection("_data", true, SectionKind::DataRel); } diff --git a/lib/Target/Alpha/AsmPrinter/AlphaAsmPrinter.cpp b/lib/Target/Alpha/AsmPrinter/AlphaAsmPrinter.cpp index 08a2c3430e..a37dee7d0c 100644 --- a/lib/Target/Alpha/AsmPrinter/AlphaAsmPrinter.cpp +++ b/lib/Target/Alpha/AsmPrinter/AlphaAsmPrinter.cpp @@ -23,6 +23,7 @@ #include "llvm/CodeGen/AsmPrinter.h" #include "llvm/CodeGen/DwarfWriter.h" #include "llvm/Target/TargetAsmInfo.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Target/TargetMachine.h" #include "llvm/Target/TargetRegistry.h" #include "llvm/Support/Compiler.h" @@ -138,7 +139,7 @@ bool AlphaAsmPrinter::runOnMachineFunction(MachineFunction &MF) { // Print out labels for the function. const Function *F = MF.getFunction(); - SwitchToSection(TAI->SectionForGlobal(F)); + SwitchToSection(getObjFileLowering().SectionForGlobal(F, TM)); EmitAlignment(MF.getAlignment(), F); switch (F->getLinkage()) { @@ -214,7 +215,7 @@ void AlphaAsmPrinter::PrintGlobalVariable(const GlobalVariable *GVar) { unsigned Align = TD->getPreferredAlignmentLog(GVar); // 0: Switch to section - SwitchToSection(TAI->SectionForGlobal(GVar)); + SwitchToSection(getObjFileLowering().SectionForGlobal(GVar, TM)); // 1: Check visibility printVisibility(name, GVar->getVisibility()); diff --git a/lib/Target/CMakeLists.txt b/lib/Target/CMakeLists.txt index 98df86cc82..f5c94f22e8 100644 --- a/lib/Target/CMakeLists.txt +++ b/lib/Target/CMakeLists.txt @@ -10,6 +10,7 @@ add_llvm_library(LLVMTarget TargetFrameInfo.cpp TargetInstrInfo.cpp TargetIntrinsicInfo.cpp + TargetLoweringObjectFile.cpp TargetMachOWriterInfo.cpp TargetMachine.cpp TargetRegisterInfo.cpp diff --git a/lib/Target/COFFTargetAsmInfo.cpp b/lib/Target/COFFTargetAsmInfo.cpp index cd7356d551..f1f742e787 100644 --- a/lib/Target/COFFTargetAsmInfo.cpp +++ b/lib/Target/COFFTargetAsmInfo.cpp @@ -19,9 +19,6 @@ using namespace llvm; COFFTargetAsmInfo::COFFTargetAsmInfo(const TargetMachine &TM) : TargetAsmInfo(TM) { - TextSection = getOrCreateSection("_text", true, SectionKind::Text); - DataSection = getOrCreateSection("_data", true, SectionKind::DataRel); - GlobalPrefix = "_"; LCOMMDirective = "\t.lcomm\t"; COMMDirectiveTakesAlignment = false; @@ -53,57 +50,3 @@ COFFTargetAsmInfo::COFFTargetAsmInfo(const TargetMachine &TM) DwarfMacroInfoSection = "\t.section\t.debug_macinfo,\"dr\""; } -void COFFTargetAsmInfo::getSectionFlagsAsString(SectionKind Kind, - SmallVectorImpl<char> &Str) const { - // FIXME: Inefficient. - std::string Res = ",\""; - if (Kind.isText()) - Res += 'x'; - if (Kind.isWriteable()) - Res += 'w'; - Res += "\""; - - Str.append(Res.begin(), Res.end()); -} - -//===----------------------------------------------------------------------===// -// Move to AsmPrinter (mangler access). -//===----------------------------------------------------------------------===// - -#include "llvm/GlobalVariable.h" - -static const char *getSectionPrefixForUniqueGlobal(SectionKind Kind) { - if (Kind.isText()) - return ".text$linkonce"; - if (Kind.isWriteable()) - return ".data$linkonce"; - return ".rdata$linkonce"; -} - -const Section * -COFFTargetAsmInfo::SelectSectionForGlobal(const GlobalValue *GV, - SectionKind Kind) const { - assert(!Kind.isThreadLocal() && "Doesn't support TLS"); - - // If this global is linkonce/weak and the target handles this by emitting it - // into a 'uniqued' section name, create and return the section now. - if (Kind.isWeak()) { - const char *Prefix = getSectionPrefixForUniqueGlobal(Kind); - // FIXME: Use mangler interface (PR4584). - std::string Name = Prefix+GV->getNameStr(); - return getOrCreateSection(Name.c_str(), false, Kind.getKind()); - } - - if (Kind.isText()) - return getTextSection(); - - if (Kind.isBSS()) - if (const Section *S = getBSSSection_()) - return S; - - if (Kind.isReadOnly()) - if (const Section *S = getReadOnlySection()) - return S; - - return getDataSection(); -} diff --git a/lib/Target/CellSPU/AsmPrinter/SPUAsmPrinter.cpp b/lib/Target/CellSPU/AsmPrinter/SPUAsmPrinter.cpp index fd1df767dc..e53543c436 100644 --- a/lib/Target/CellSPU/AsmPrinter/SPUAsmPrinter.cpp +++ b/lib/Target/CellSPU/AsmPrinter/SPUAsmPrinter.cpp @@ -34,9 +34,10 @@ #include "llvm/Support/Compiler.h" #include "llvm/Support/FormattedStream.h" #include "llvm/Target/TargetAsmInfo.h" -#include "llvm/Target/TargetRegisterInfo.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Target/TargetInstrInfo.h" #include "llvm/Target/TargetOptions.h" +#include "llvm/Target/TargetRegisterInfo.h" #include "llvm/Target/TargetRegistry.h" #include "llvm/ADT/Statistic.h" #include "llvm/ADT/StringExtras.h" @@ -427,7 +428,7 @@ LinuxAsmPrinter::runOnMachineFunction(MachineFunction &MF) // Print out labels for the function. const Function *F = MF.getFunction(); - SwitchToSection(TAI->SectionForGlobal(F)); + SwitchToSection(getObjFileLowering().SectionForGlobal(F, TM)); EmitAlignment(MF.getAlignment(), F); switch (F->getLinkage()) { @@ -525,7 +526,7 @@ void LinuxAsmPrinter::PrintGlobalVariable(const GlobalVariable *GVar) { unsigned Size = TD->getTypeAllocSize(Type); unsigned Align = TD->getPreferredAlignmentLog(GVar); - SwitchToSection(TAI->SectionForGlobal(GVar)); + SwitchToSection(getObjFileLowering().SectionForGlobal(GVar, TM)); if (C->isNullValue() && /* FIXME: Verify correct */ !GVar->hasSection() && diff --git a/lib/Target/CellSPU/SPUISelLowering.cpp b/lib/Target/CellSPU/SPUISelLowering.cpp index d0aad070c2..50ba00f636 100644 --- a/lib/Target/CellSPU/SPUISelLowering.cpp +++ b/lib/Target/CellSPU/SPUISelLowering.cpp @@ -15,8 +15,9 @@ #include "SPUISelLowering.h" #include "SPUTargetMachine.h" #include "SPUFrameInfo.h" -#include "llvm/ADT/APInt.h" -#include "llvm/ADT/VectorExtras.h" +#include "llvm/Constants.h" +#include "llvm/Function.h" +#include "llvm/Intrinsics.h" #include "llvm/CallingConv.h" #include "llvm/CodeGen/CallingConvLower.h" #include "llvm/CodeGen/MachineFrameInfo.h" @@ -24,15 +25,13 @@ #include "llvm/CodeGen/MachineInstrBuilder.h" #include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/CodeGen/SelectionDAG.h" -#include "llvm/Constants.h" -#include "llvm/Function.h" -#include "llvm/Intrinsics.h" +#include "llvm/Target/TargetLoweringObjectFile.h" +#include "llvm/Target/TargetOptions.h" +#include "llvm/ADT/VectorExtras.h" #include "llvm/Support/Debug.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/MathExtras.h" #include "llvm/Support/raw_ostream.h" -#include "llvm/Target/TargetOptions.h" - #include <map> using namespace llvm; @@ -125,9 +124,8 @@ namespace { } SPUTargetLowering::SPUTargetLowering(SPUTargetMachine &TM) - : TargetLowering(TM), - SPUTM(TM) -{ + : TargetLowering(TM, new TargetLoweringObjectFileELF()), + SPUTM(TM) { // Fold away setcc operations if possible. setPow2DivIsCheap(); diff --git a/lib/Target/CellSPU/SPUTargetAsmInfo.cpp b/lib/Target/CellSPU/SPUTargetAsmInfo.cpp index 534d18e60f..1d71605954 100644 --- a/lib/Target/CellSPU/SPUTargetAsmInfo.cpp +++ b/lib/Target/CellSPU/SPUTargetAsmInfo.cpp @@ -33,10 +33,6 @@ SPULinuxTargetAsmInfo::SPULinuxTargetAsmInfo(const SPUTargetMachine &TM) : HasLEB128 = true; HasDotLocAndDotFile = true; - // BSS section needs to be emitted as ".section" - BSSSection = "\t.section\t.bss"; - BSSSection_ = getOrCreateSection("\t.bss", false, SectionKind::BSS); - SupportsDebugInformation = true; NeedsSet = true; DwarfAbbrevSection = "\t.section .debug_abbrev,\"\",@progbits"; diff --git a/lib/Target/DarwinTargetAsmInfo.cpp b/lib/Target/DarwinTargetAsmInfo.cpp index 5429e65926..aa93c0d119 100644 --- a/lib/Target/DarwinTargetAsmInfo.cpp +++ b/lib/Target/DarwinTargetAsmInfo.cpp @@ -27,32 +27,7 @@ using namespace llvm; DarwinTargetAsmInfo::DarwinTargetAsmInfo(const TargetMachine &TM) : TargetAsmInfo(TM) { - TextSection = getOrCreateSection("\t.text", true, SectionKind::Text); - DataSection = getOrCreateSection("\t.data", true, SectionKind::DataRel); - - CStringSection_ = getOrCreateSection("\t.cstring", true, - SectionKind::MergeableCString); - FourByteConstantSection = getOrCreateSection("\t.literal4\n", true, - SectionKind::MergeableConst4); - EightByteConstantSection = getOrCreateSection("\t.literal8\n", true, - SectionKind::MergeableConst8); - SixteenByteConstantSection = - getOrCreateSection("\t.literal16\n", true, SectionKind::MergeableConst16); - - ReadOnlySection = getOrCreateSection("\t.const", true, SectionKind::ReadOnly); - - TextCoalSection = - getOrCreateSection("\t__TEXT,__textcoal_nt,coalesced,pure_instructions", - false, SectionKind::Text); - ConstTextCoalSection = getOrCreateSection("\t__TEXT,__const_coal,coalesced", - false, SectionKind::Text); - ConstDataCoalSection = getOrCreateSection("\t__DATA,__const_coal,coalesced", - false, SectionKind::Text); - ConstDataSection = getOrCreateSection("\t.const_data", true, - SectionKind::ReadOnlyWithRel); - DataCoalSection = getOrCreateSection("\t__DATA,__datacoal_nt,coalesced", - false, SectionKind::DataRel); - + // Common settings for all Darwin targets. // Syntax: GlobalPrefix = "_"; @@ -124,79 +99,3 @@ bool DarwinTargetAsmInfo::emitUsedDirectiveFor(const GlobalValue* GV, return true; } -const Section* -DarwinTargetAsmInfo::SelectSectionForGlobal(const GlobalValue *GV, - SectionKind Kind) const { - assert(!Kind.isThreadLocal() && "Darwin doesn't support TLS"); - - if (Kind.isText()) - return Kind.isWeak() ? TextCoalSection : TextSection; - - // If this is weak/linkonce, put this in a coalescable section, either in text - // or data depending on if it is writable. - if (Kind.isWeak()) { - if (Kind.isReadOnly()) - return ConstTextCoalSection; - return DataCoalSection; - } - - // FIXME: Alignment check should be handled by section classifier. - if (Kind.isMergeableCString()) - return MergeableStringSection(cast<GlobalVariable>(GV)); - - if (Kind.isMergeableConst()) { - if (Kind.isMergeableConst4()) - return FourByteConstantSection; - if (Kind.isMergeableConst8()) - return EightByteConstantSection; - if (Kind.isMergeableConst16()) - return SixteenByteConstantSection; - return ReadOnlySection; // .const - } - - // FIXME: ROData -> const in -static mode that is relocatable but they happen - // by the static linker. Why not mergeable? - if (Kind.isReadOnly()) - return getReadOnlySection(); - - // If this is marked const, put it into a const section. But if the dynamic - // linker needs to write to it, put it in the data segment. - if (Kind.isReadOnlyWithRel()) - return ConstDataSection; - - // Otherwise, just drop the variable in the normal data section. - return DataSection; -} - -const Section* -DarwinTargetAsmInfo::MergeableStringSection(const GlobalVariable *GV) const { - const TargetData *TD = TM.getTargetData(); - Constant *C = cast<GlobalVariable>(GV)->getInitializer(); - const Type *Ty = cast<ArrayType>(C->getType())->getElementType(); - - unsigned Size = TD->getTypeAllocSize(Ty); - if (Size) { - unsigned Align = TD->getPreferredAlignment(GV); - if (Align <= 32) - return getCStringSection_(); - } - - return getReadOnlySection(); -} - -const Section * -DarwinTargetAsmInfo::getSectionForMergeableConstant(SectionKind Kind) const { - // If this constant requires a relocation, we have to put it in the data - // segment, not in the text segment. - if (Kind.isDataRel()) - return ConstDataSection; - - if (Kind.isMergeableConst4()) - return FourByteConstantSection; - if (Kind.isMergeableConst8()) - return EightByteConstantSection; - if (Kind.isMergeableConst16()) - return SixteenByteConstantSection; - return ReadOnlySection; // .const -} - diff --git a/lib/Target/ELFTargetAsmInfo.cpp b/lib/Target/ELFTargetAsmInfo.cpp index 556b494185..e3259bd916 100644 --- a/lib/Target/ELFTargetAsmInfo.cpp +++ b/lib/Target/ELFTargetAsmInfo.cpp @@ -18,217 +18,4 @@ using namespace llvm; ELFTargetAsmInfo::ELFTargetAsmInfo(const TargetMachine &TM) : TargetAsmInfo(TM) { - - TextSection = getOrCreateSection("\t.text", true, SectionKind::Text); - DataSection = getOrCreateSection("\t.data", true, SectionKind::DataRel); - ReadOnlySection = - getOrCreateSection("\t.rodata", false, SectionKind::ReadOnly); - TLSDataSection = - getOrCreateSection("\t.tdata", false, SectionKind::ThreadData); - TLSBSSSection = getOrCreateSection("\t.tbss", false, SectionKind::ThreadBSS); - - DataRelSection = getOrCreateSection("\t.data.rel", false, - SectionKind::DataRel); - DataRelLocalSection = getOrCreateSection("\t.data.rel.local", false, - SectionKind::DataRelLocal); - DataRelROSection = getOrCreateSection("\t.data.rel.ro", false, - SectionKind::ReadOnlyWithRel); - DataRelROLocalSection = - getOrCreateSection("\t.data.rel.ro.local", false, - SectionKind::ReadOnlyWithRelLocal); - - MergeableConst4Section = getOrCreateSection(".rodata.cst4", false, - SectionKind::MergeableConst4); - MergeableConst8Section = getOrCreateSection(".rodata.cst8", false, - SectionKind::MergeableConst8); - MergeableConst16Section = getOrCreateSection(".rodata.cst16", false, - SectionKind::MergeableConst16); -} - -/// getFlagsForNamedSection - If this target wants to be able to infer -/// section flags based on the name of the section specified for a global -/// variable, it can implement this. -SectionKind::Kind ELFTargetAsmInfo::getKindForNamedSection(const char *Name, - SectionKind::Kind K) const { - if (Name[0] != '.') return K; - - // Some lame default implementation based on some magic section names. - if (strncmp(Name, ".gnu.linkonce.b.", 16) == 0 || - strncmp(Name, ".llvm.linkonce.b.", 17) == 0 || - strncmp(Name, ".gnu.linkonce.sb.", 17) == 0 || - strncmp(Name, ".llvm.linkonce.sb.", 18) == 0) - return SectionKind::BSS; - - if (strcmp(Name, ".tdata") == 0 || - strncmp(Name, ".tdata.", 7) == 0 || - strncmp(Name, ".gnu.linkonce.td.", 17) == 0 || - strncmp(Name, ".llvm.linkonce.td.", 18) == 0) - return SectionKind::ThreadData; - - if (strcmp(Name, ".tbss") == 0 || - strncmp(Name, ".tbss.", 6) == 0 || - strncmp(Name, ".gnu.linkonce.tb.", 17) == 0 || - strncmp(Name, ".llvm.linkonce.tb.", 18) == 0) - return SectionKind::ThreadBSS; - - return K; -} - - -void ELFTargetAsmInfo::getSectionFlagsAsString(SectionKind Kind, - SmallVectorImpl<char> &Str) const { - Str.push_back(','); - Str.push_back('"'); - - if (!Kind.isMetadata()) - Str.push_back('a'); - if (Kind.isText()) - Str.push_back('x'); - if (Kind.isWriteable()) - Str.push_back('w'); - if (Kind.isMergeableConst() || Kind.isMergeableCString()) - Str.push_back('M'); - if (Kind.isMergeableCString()) - Str.push_back('S'); - if (Kind.isThreadLocal()) - Str.push_back('T'); - - Str.push_back('"'); - Str.push_back(','); - - // If comment string is '@', e.g. as on ARM - use '%' instead - if (strcmp(Comment |