| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 1 | //===-- DarwinTargetAsmInfo.cpp - Darwin asm properties ---------*- C++ -*-===// | 
 | 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 | // | 
 | 10 | // This file defines target asm properties related what form asm statements | 
 | 11 | // should take in general on Darwin-based targets | 
 | 12 | // | 
 | 13 | //===----------------------------------------------------------------------===// | 
 | 14 |  | 
 | 15 | #include "llvm/Constants.h" | 
 | 16 | #include "llvm/DerivedTypes.h" | 
 | 17 | #include "llvm/Function.h" | 
 | 18 | #include "llvm/GlobalVariable.h" | 
 | 19 | #include "llvm/ADT/StringExtras.h" | 
| Dale Johannesen | d2e51af | 2008-09-09 22:29:13 +0000 | [diff] [blame] | 20 | #include "llvm/Support/Mangler.h" | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 21 | #include "llvm/Target/DarwinTargetAsmInfo.h" | 
 | 22 | #include "llvm/Target/TargetMachine.h" | 
 | 23 | #include "llvm/Target/TargetData.h" | 
 | 24 |  | 
 | 25 | using namespace llvm; | 
 | 26 |  | 
| Dan Gohman | 8f09225 | 2008-11-03 18:22:42 +0000 | [diff] [blame] | 27 | DarwinTargetAsmInfo::DarwinTargetAsmInfo(const TargetMachine &TM)  | 
 | 28 |   : TargetAsmInfo(TM) { | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 29 |  | 
 | 30 |   CStringSection_ = getUnnamedSection("\t.cstring", | 
 | 31 |                                 SectionFlags::Mergeable | SectionFlags::Strings); | 
| Anton Korobeynikov | 6481873 | 2008-09-24 22:18:54 +0000 | [diff] [blame] | 32 |   FourByteConstantSection = getUnnamedSection("\t.literal4\n", | 
 | 33 |                                               SectionFlags::Mergeable); | 
 | 34 |   EightByteConstantSection = getUnnamedSection("\t.literal8\n", | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 35 |                                                SectionFlags::Mergeable); | 
| Anton Korobeynikov | ae408e6 | 2008-07-19 13:16:11 +0000 | [diff] [blame] | 36 |  | 
| Anton Korobeynikov | cff2ea0 | 2008-07-19 13:15:46 +0000 | [diff] [blame] | 37 |   // Note: 16-byte constant section is subtarget specific and should be provided | 
| Anton Korobeynikov | 6481873 | 2008-09-24 22:18:54 +0000 | [diff] [blame] | 38 |   // there, if needed. | 
 | 39 |   SixteenByteConstantSection = 0; | 
| Anton Korobeynikov | cff2ea0 | 2008-07-19 13:15:46 +0000 | [diff] [blame] | 40 |  | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 41 |   ReadOnlySection = getUnnamedSection("\t.const\n", SectionFlags::None); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 42 |  | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 43 |   TextCoalSection = | 
| Anton Korobeynikov | d79cda9 | 2008-09-24 22:19:13 +0000 | [diff] [blame] | 44 |     getNamedSection("\t__TEXT,__textcoal_nt,coalesced,pure_instructions", | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 45 |                     SectionFlags::Code); | 
| Dale Johannesen | 585457e | 2008-10-08 21:49:47 +0000 | [diff] [blame] | 46 |   ConstTextCoalSection = getNamedSection("\t__TEXT,__const_coal,coalesced", | 
 | 47 |                                          SectionFlags::None); | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 48 |   ConstDataCoalSection = getNamedSection("\t__DATA,__const_coal,coalesced", | 
| Anton Korobeynikov | d79cda9 | 2008-09-24 22:19:13 +0000 | [diff] [blame] | 49 |                                          SectionFlags::None); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 50 |   ConstDataSection = getUnnamedSection(".const_data", SectionFlags::None); | 
| Anton Korobeynikov | d79cda9 | 2008-09-24 22:19:13 +0000 | [diff] [blame] | 51 |   DataCoalSection = getNamedSection("\t__DATA,__datacoal_nt,coalesced", | 
 | 52 |                                     SectionFlags::Writeable); | 
| Chris Lattner | 4e0f25b | 2009-06-19 00:08:39 +0000 | [diff] [blame] | 53 |      | 
 | 54 |    | 
 | 55 |   // Common settings for all Darwin targets. | 
 | 56 |   // Syntax: | 
 | 57 |   GlobalPrefix = "_"; | 
 | 58 |   PrivateGlobalPrefix = "L"; | 
 | 59 |   LessPrivateGlobalPrefix = "l";  // Marker for some ObjC metadata | 
 | 60 |   StringConstantPrefix = "\1LC"; | 
 | 61 |   NeedsSet = true; | 
 | 62 |   NeedsIndirectEncoding = true; | 
 | 63 |   AllowQuotesInName = true; | 
 | 64 |   HasSingleParameterDotFile = false; | 
 | 65 |  | 
 | 66 |   // In non-PIC modes, emit a special label before jump tables so that the | 
 | 67 |   // linker can perform more accurate dead code stripping.  We do not check the | 
 | 68 |   // relocation model here since it can be overridden later. | 
 | 69 |   JumpTableSpecialLabelPrefix = "l"; | 
 | 70 |      | 
 | 71 |   // Directives: | 
 | 72 |   WeakDefDirective = "\t.weak_definition "; | 
 | 73 |   WeakRefDirective = "\t.weak_reference "; | 
 | 74 |   HiddenDirective = "\t.private_extern "; | 
 | 75 |      | 
 | 76 |   // Sections: | 
 | 77 |   CStringSection = "\t.cstring"; | 
 | 78 |   JumpTableDataSection = "\t.const\n"; | 
 | 79 |   BSSSection = 0; | 
 | 80 |  | 
 | 81 |   if (TM.getRelocationModel() == Reloc::Static) { | 
 | 82 |     StaticCtorsSection = ".constructor"; | 
 | 83 |     StaticDtorsSection = ".destructor"; | 
 | 84 |   } else { | 
 | 85 |     StaticCtorsSection = ".mod_init_func"; | 
 | 86 |     StaticDtorsSection = ".mod_term_func"; | 
 | 87 |   } | 
 | 88 |      | 
 | 89 |   DwarfAbbrevSection = ".section __DWARF,__debug_abbrev,regular,debug"; | 
 | 90 |   DwarfInfoSection = ".section __DWARF,__debug_info,regular,debug"; | 
 | 91 |   DwarfLineSection = ".section __DWARF,__debug_line,regular,debug"; | 
 | 92 |   DwarfFrameSection = ".section __DWARF,__debug_frame,regular,debug"; | 
 | 93 |   DwarfPubNamesSection = ".section __DWARF,__debug_pubnames,regular,debug"; | 
 | 94 |   DwarfPubTypesSection = ".section __DWARF,__debug_pubtypes,regular,debug"; | 
 | 95 |   DwarfStrSection = ".section __DWARF,__debug_str,regular,debug"; | 
 | 96 |   DwarfLocSection = ".section __DWARF,__debug_loc,regular,debug"; | 
 | 97 |   DwarfARangesSection = ".section __DWARF,__debug_aranges,regular,debug"; | 
 | 98 |   DwarfRangesSection = ".section __DWARF,__debug_ranges,regular,debug"; | 
 | 99 |   DwarfMacroInfoSection = ".section __DWARF,__debug_macinfo,regular,debug"; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 100 | } | 
 | 101 |  | 
| Dale Johannesen | d2e51af | 2008-09-09 22:29:13 +0000 | [diff] [blame] | 102 | /// emitUsedDirectiveFor - On Darwin, internally linked data beginning with | 
 | 103 | /// the PrivateGlobalPrefix or the LessPrivateGlobalPrefix does not have the | 
 | 104 | /// directive emitted (this occurs in ObjC metadata). | 
 | 105 |  | 
 | 106 | bool | 
 | 107 | DarwinTargetAsmInfo::emitUsedDirectiveFor(const GlobalValue* GV, | 
 | 108 |                                           Mangler *Mang) const { | 
 | 109 |   if (GV==0) | 
 | 110 |     return false; | 
| Rafael Espindola | bb46f52 | 2009-01-15 20:18:42 +0000 | [diff] [blame] | 111 |   if (GV->hasLocalLinkage() && !isa<Function>(GV) && | 
| Dale Johannesen | d2e51af | 2008-09-09 22:29:13 +0000 | [diff] [blame] | 112 |       ((strlen(getPrivateGlobalPrefix()) != 0 && | 
 | 113 |         Mang->getValueName(GV).substr(0,strlen(getPrivateGlobalPrefix())) == | 
 | 114 |           getPrivateGlobalPrefix()) || | 
 | 115 |        (strlen(getLessPrivateGlobalPrefix()) != 0 && | 
 | 116 |         Mang->getValueName(GV).substr(0,strlen(getLessPrivateGlobalPrefix())) == | 
 | 117 |           getLessPrivateGlobalPrefix()))) | 
 | 118 |     return false; | 
 | 119 |   return true; | 
 | 120 | } | 
 | 121 |  | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 122 | const Section* | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 123 | DarwinTargetAsmInfo::SelectSectionForGlobal(const GlobalValue *GV) const { | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 124 |   SectionKind::Kind Kind = SectionKindForGlobal(GV); | 
| Duncan Sands | 667d4b8 | 2009-03-07 15:45:40 +0000 | [diff] [blame] | 125 |   bool isWeak = GV->isWeakForLinker(); | 
| Dan Gohman | 8f09225 | 2008-11-03 18:22:42 +0000 | [diff] [blame] | 126 |   bool isNonStatic = TM.getRelocationModel() != Reloc::Static; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 127 |  | 
 | 128 |   switch (Kind) { | 
 | 129 |    case SectionKind::Text: | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 130 |     if (isWeak) | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 131 |       return TextCoalSection; | 
 | 132 |     else | 
| Anton Korobeynikov | 0b501d1 | 2008-09-24 22:16:33 +0000 | [diff] [blame] | 133 |       return TextSection; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 134 |    case SectionKind::Data: | 
 | 135 |    case SectionKind::ThreadData: | 
 | 136 |    case SectionKind::BSS: | 
 | 137 |    case SectionKind::ThreadBSS: | 
 | 138 |     if (cast<GlobalVariable>(GV)->isConstant()) | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 139 |       return (isWeak ? ConstDataCoalSection : ConstDataSection); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 140 |     else | 
| Anton Korobeynikov | 0b501d1 | 2008-09-24 22:16:33 +0000 | [diff] [blame] | 141 |       return (isWeak ? DataCoalSection : DataSection); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 142 |    case SectionKind::ROData: | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 143 |     return (isWeak ? ConstDataCoalSection : | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 144 |             (isNonStatic ? ConstDataSection : getReadOnlySection())); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 145 |    case SectionKind::RODataMergeStr: | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 146 |     return (isWeak ? | 
| Dale Johannesen | 585457e | 2008-10-08 21:49:47 +0000 | [diff] [blame] | 147 |             ConstTextCoalSection : | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 148 |             MergeableStringSection(cast<GlobalVariable>(GV))); | 
 | 149 |    case SectionKind::RODataMergeConst: | 
| Evan Cheng | 42ccc21 | 2008-08-08 17:56:50 +0000 | [diff] [blame] | 150 |     return (isWeak ? | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 151 |             ConstDataCoalSection: | 
 | 152 |             MergeableConstSection(cast<GlobalVariable>(GV))); | 
 | 153 |    default: | 
 | 154 |     assert(0 && "Unsuported section kind for global"); | 
 | 155 |   } | 
 | 156 |  | 
 | 157 |   // FIXME: Do we have any extra special weird cases? | 
| Devang Patel | 8a84e44 | 2009-01-05 17:31:22 +0000 | [diff] [blame] | 158 |   return NULL; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 159 | } | 
 | 160 |  | 
 | 161 | const Section* | 
 | 162 | DarwinTargetAsmInfo::MergeableStringSection(const GlobalVariable *GV) const { | 
| Dan Gohman | 8f09225 | 2008-11-03 18:22:42 +0000 | [diff] [blame] | 163 |   const TargetData *TD = TM.getTargetData(); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 164 |   Constant *C = cast<GlobalVariable>(GV)->getInitializer(); | 
| Anton Korobeynikov | 72bb402 | 2009-01-27 22:29:24 +0000 | [diff] [blame] | 165 |   const Type *Ty = cast<ArrayType>(C->getType())->getElementType(); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 166 |  | 
| Duncan Sands | 777d230 | 2009-05-09 07:06:46 +0000 | [diff] [blame] | 167 |   unsigned Size = TD->getTypeAllocSize(Ty); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 168 |   if (Size) { | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 169 |     unsigned Align = TD->getPreferredAlignment(GV); | 
 | 170 |     if (Align <= 32) | 
 | 171 |       return getCStringSection_(); | 
 | 172 |   } | 
 | 173 |  | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 174 |   return getReadOnlySection(); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 175 | } | 
 | 176 |  | 
 | 177 | const Section* | 
 | 178 | DarwinTargetAsmInfo::MergeableConstSection(const GlobalVariable *GV) const { | 
| Anton Korobeynikov | dbab2d2 | 2008-09-24 22:17:27 +0000 | [diff] [blame] | 179 |   Constant *C = GV->getInitializer(); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 180 |  | 
| Anton Korobeynikov | 84e160e | 2008-08-07 09:51:02 +0000 | [diff] [blame] | 181 |   return MergeableConstSection(C->getType()); | 
 | 182 | } | 
 | 183 |  | 
 | 184 | inline const Section* | 
 | 185 | DarwinTargetAsmInfo::MergeableConstSection(const Type *Ty) const { | 
| Dan Gohman | 8f09225 | 2008-11-03 18:22:42 +0000 | [diff] [blame] | 186 |   const TargetData *TD = TM.getTargetData(); | 
| Anton Korobeynikov | 84e160e | 2008-08-07 09:51:02 +0000 | [diff] [blame] | 187 |  | 
| Duncan Sands | 777d230 | 2009-05-09 07:06:46 +0000 | [diff] [blame] | 188 |   unsigned Size = TD->getTypeAllocSize(Ty); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 189 |   if (Size == 4) | 
| Anton Korobeynikov | 6481873 | 2008-09-24 22:18:54 +0000 | [diff] [blame] | 190 |     return FourByteConstantSection; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 191 |   else if (Size == 8) | 
| Anton Korobeynikov | 6481873 | 2008-09-24 22:18:54 +0000 | [diff] [blame] | 192 |     return EightByteConstantSection; | 
 | 193 |   else if (Size == 16 && SixteenByteConstantSection) | 
 | 194 |     return SixteenByteConstantSection; | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 195 |  | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 196 |   return getReadOnlySection(); | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 197 | } | 
 | 198 |  | 
| Anton Korobeynikov | 84e160e | 2008-08-07 09:51:02 +0000 | [diff] [blame] | 199 | const Section* | 
 | 200 | DarwinTargetAsmInfo::SelectSectionForMachineConst(const Type *Ty) const { | 
 | 201 |   const Section* S = MergeableConstSection(Ty); | 
 | 202 |  | 
 | 203 |   // Handle weird special case, when compiling PIC stuff. | 
| Anton Korobeynikov | 00181a3 | 2008-09-24 22:20:27 +0000 | [diff] [blame] | 204 |   if (S == getReadOnlySection() && | 
| Dan Gohman | 8f09225 | 2008-11-03 18:22:42 +0000 | [diff] [blame] | 205 |       TM.getRelocationModel() != Reloc::Static) | 
| Anton Korobeynikov | 84e160e | 2008-08-07 09:51:02 +0000 | [diff] [blame] | 206 |     return ConstDataSection; | 
 | 207 |  | 
 | 208 |   return S; | 
 | 209 | } | 
 | 210 |  | 
| Anton Korobeynikov | 745e864 | 2008-07-19 13:14:46 +0000 | [diff] [blame] | 211 | std::string | 
 | 212 | DarwinTargetAsmInfo::UniqueSectionForGlobal(const GlobalValue* GV, | 
 | 213 |                                                SectionKind::Kind kind) const { | 
 | 214 |   assert(0 && "Darwin does not use unique sections"); | 
 | 215 |   return ""; | 
 | 216 | } |