1 //===-- HexagonTargetObjectFile.cpp ---------------------------------------===// 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 contains the declarations of the HexagonTargetAsmInfo properties. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #define DEBUG_TYPE "hexagon-sdata" 15 16 #include "HexagonTargetObjectFile.h" 17 #include "llvm/ADT/SmallString.h" 18 #include "llvm/ADT/StringRef.h" 19 #include "llvm/ADT/Twine.h" 20 #include "llvm/IR/DataLayout.h" 21 #include "llvm/IR/DerivedTypes.h" 22 #include "llvm/IR/GlobalObject.h" 23 #include "llvm/IR/GlobalValue.h" 24 #include "llvm/IR/GlobalVariable.h" 25 #include "llvm/IR/Type.h" 26 #include "llvm/MC/MCContext.h" 27 #include "llvm/MC/SectionKind.h" 28 #include "llvm/Support/Casting.h" 29 #include "llvm/Support/CommandLine.h" 30 #include "llvm/Support/Debug.h" 31 #include "llvm/Support/ELF.h" 32 #include "llvm/Support/raw_ostream.h" 33 #include "llvm/Target/TargetMachine.h" 34 35 using namespace llvm; 36 37 static cl::opt<unsigned> SmallDataThreshold("hexagon-small-data-threshold", 38 cl::init(8), cl::Hidden, 39 cl::desc("The maximum size of an object in the sdata section")); 40 41 static cl::opt<bool> NoSmallDataSorting("mno-sort-sda", cl::init(false), 42 cl::Hidden, cl::desc("Disable small data sections sorting")); 43 44 static cl::opt<bool> StaticsInSData("hexagon-statics-in-small-data", 45 cl::init(false), cl::Hidden, cl::ZeroOrMore, 46 cl::desc("Allow static variables in .sdata")); 47 48 static cl::opt<bool> TraceGVPlacement("trace-gv-placement", 49 cl::Hidden, cl::init(false), 50 cl::desc("Trace global value placement")); 51 52 // TraceGVPlacement controls messages for all builds. For builds with assertions 53 // (debug or release), messages are also controlled by the usual debug flags 54 // (e.g. -debug and -debug-only=globallayout) 55 #define TRACE_TO(s, X) s << X 56 #ifdef NDEBUG 57 #define TRACE(X) \ 58 do { \ 59 if (TraceGVPlacement) { \ 60 TRACE_TO(errs(), X); \ 61 } \ 62 } while (false) 63 #else 64 #define TRACE(X) \ 65 do { \ 66 if (TraceGVPlacement) { \ 67 TRACE_TO(errs(), X); \ 68 } else { \ 69 DEBUG(TRACE_TO(dbgs(), X)); \ 70 } \ 71 } while (false) 72 #endif 73 74 // Returns true if the section name is such that the symbol will be put 75 // in a small data section. 76 // For instance, global variables with section attributes such as ".sdata" 77 // ".sdata.*", ".sbss", and ".sbss.*" will go into small data. 78 static bool isSmallDataSection(StringRef Sec) { 79 // sectionName is either ".sdata" or ".sbss". Looking for an exact match 80 // obviates the need for checks for section names such as ".sdatafoo". 81 if (Sec.equals(".sdata") || Sec.equals(".sbss") || Sec.equals(".scommon")) 82 return true; 83 // If either ".sdata." or ".sbss." is a substring of the section name 84 // then put the symbol in small data. 85 return Sec.find(".sdata.") != StringRef::npos || 86 Sec.find(".sbss.") != StringRef::npos || 87 Sec.find(".scommon.") != StringRef::npos; 88 } 89 90 static const char *getSectionSuffixForSize(unsigned Size) { 91 switch (Size) { 92 default: 93 return ""; 94 case 1: 95 return ".1"; 96 case 2: 97 return ".2"; 98 case 4: 99 return ".4"; 100 case 8: 101 return ".8"; 102 } 103 } 104 105 void HexagonTargetObjectFile::Initialize(MCContext &Ctx, 106 const TargetMachine &TM) { 107 TargetLoweringObjectFileELF::Initialize(Ctx, TM); 108 InitializeELF(TM.Options.UseInitArray); 109 110 SmallDataSection = 111 getContext().getELFSection(".sdata", ELF::SHT_PROGBITS, 112 ELF::SHF_WRITE | ELF::SHF_ALLOC | 113 ELF::SHF_HEX_GPREL); 114 SmallBSSSection = 115 getContext().getELFSection(".sbss", ELF::SHT_NOBITS, 116 ELF::SHF_WRITE | ELF::SHF_ALLOC | 117 ELF::SHF_HEX_GPREL); 118 } 119 120 MCSection *HexagonTargetObjectFile::SelectSectionForGlobal( 121 const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const { 122 TRACE("[SelectSectionForGlobal] GO(" << GO->getName() << ") "); 123 TRACE("input section(" << GO->getSection() << ") "); 124 125 TRACE((GO->hasPrivateLinkage() ? "private_linkage " : "") 126 << (GO->hasLocalLinkage() ? "local_linkage " : "") 127 << (GO->hasInternalLinkage() ? "internal " : "") 128 << (GO->hasExternalLinkage() ? "external " : "") 129 << (GO->hasCommonLinkage() ? "common_linkage " : "") 130 << (GO->hasCommonLinkage() ? "common " : "" ) 131 << (Kind.isCommon() ? "kind_common " : "" ) 132 << (Kind.isBSS() ? "kind_bss " : "" ) 133 << (Kind.isBSSLocal() ? "kind_bss_local " : "" )); 134 135 if (isGlobalInSmallSection(GO, TM)) 136 return selectSmallSectionForGlobal(GO, Kind, TM); 137 138 if (Kind.isCommon()) { 139 // This is purely for LTO+Linker Script because commons don't really have a 140 // section. However, the BitcodeSectionWriter pass will query for the 141 // sections of commons (and the linker expects us to know their section) so 142 // we'll return one here. 143 return BSSSection; 144 } 145 146 TRACE("default_ELF_section\n"); 147 // Otherwise, we work the same as ELF. 148 return TargetLoweringObjectFileELF::SelectSectionForGlobal(GO, Kind, TM); 149 } 150 151 MCSection *HexagonTargetObjectFile::getExplicitSectionGlobal( 152 const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const { 153 TRACE("[getExplicitSectionGlobal] GO(" << GO->getName() << ") from(" 154 << GO->getSection() << ") "); 155 TRACE((GO->hasPrivateLinkage() ? "private_linkage " : "") 156 << (GO->hasLocalLinkage() ? "local_linkage " : "") 157 << (GO->hasInternalLinkage() ? "internal " : "") 158 << (GO->hasExternalLinkage() ? "external " : "") 159 << (GO->hasCommonLinkage() ? "common_linkage " : "") 160 << (GO->hasCommonLinkage() ? "common " : "" ) 161 << (Kind.isCommon() ? "kind_common " : "" ) 162 << (Kind.isBSS() ? "kind_bss " : "" ) 163 << (Kind.isBSSLocal() ? "kind_bss_local " : "" )); 164 165 if (GO->hasSection()) { 166 StringRef Section = GO->getSection(); 167 if (Section.find(".access.text.group") != StringRef::npos) 168 return getContext().getELFSection(GO->getSection(), ELF::SHT_PROGBITS, 169 ELF::SHF_ALLOC | ELF::SHF_EXECINSTR); 170 if (Section.find(".access.data.group") != StringRef::npos) 171 return getContext().getELFSection(GO->getSection(), ELF::SHT_PROGBITS, 172 ELF::SHF_WRITE | ELF::SHF_ALLOC); 173 } 174 175 if (isGlobalInSmallSection(GO, TM)) 176 return selectSmallSectionForGlobal(GO, Kind, TM); 177 178 // Otherwise, we work the same as ELF. 179 TRACE("default_ELF_section\n"); 180 return TargetLoweringObjectFileELF::getExplicitSectionGlobal(GO, Kind, TM); 181 } 182 183 /// Return true if this global value should be placed into small data/bss 184 /// section. 185 bool HexagonTargetObjectFile::isGlobalInSmallSection(const GlobalObject *GO, 186 const TargetMachine &TM) const { 187 // Only global variables, not functions. 188 DEBUG(dbgs() << "Checking if value is in small-data, -G" 189 << SmallDataThreshold << ": \"" << GO->getName() << "\": "); 190 const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GO); 191 if (!GVar) { 192 DEBUG(dbgs() << "no, not a global variable\n"); 193 return false; 194 } 195 196 // Globals with external linkage that have an original section set must be 197 // emitted to that section, regardless of whether we would put them into 198 // small data or not. This is how we can support mixing -G0/-G8 in LTO. 199 if (GVar->hasSection()) { 200 bool IsSmall = isSmallDataSection(GVar->getSection()); 201 DEBUG(dbgs() << (IsSmall ? "yes" : "no") << ", has section: " 202 << GVar->getSection() << '\n'); 203 return IsSmall; 204 } 205 206 if (GVar->isConstant()) { 207 DEBUG(dbgs() << "no, is a constant\n"); 208 return false; 209 } 210 211 bool IsLocal = GVar->hasLocalLinkage(); 212 if (!StaticsInSData && IsLocal) { 213 DEBUG(dbgs() << "no, is static\n"); 214 return false; 215 } 216 217 Type *GType = GVar->getType(); 218 if (PointerType *PT = dyn_cast<PointerType>(GType)) 219 GType = PT->getElementType(); 220 221 if (isa<ArrayType>(GType)) { 222 DEBUG(dbgs() << "no, is an array\n"); 223 return false; 224 } 225 226 // If the type is a struct with no body provided, treat is conservatively. 227 // There cannot be actual definitions of object of such a type in this CU 228 // (only references), so assuming that they are not in sdata is safe. If 229 // these objects end up in the sdata, the references will still be valid. 230 if (StructType *ST = dyn_cast<StructType>(GType)) { 231 if (ST->isOpaque()) { 232 DEBUG(dbgs() << "no, has opaque type\n"); 233 return false; 234 } 235 } 236 237 unsigned Size = GVar->getParent()->getDataLayout().getTypeAllocSize(GType); 238 if (Size == 0) { 239 DEBUG(dbgs() << "no, has size 0\n"); 240 return false; 241 } 242 if (Size > SmallDataThreshold) { 243 DEBUG(dbgs() << "no, size exceeds sdata threshold: " << Size << '\n'); 244 return false; 245 } 246 247 DEBUG(dbgs() << "yes\n"); 248 return true; 249 } 250 251 bool HexagonTargetObjectFile::isSmallDataEnabled() const { 252 return SmallDataThreshold > 0; 253 } 254 255 unsigned HexagonTargetObjectFile::getSmallDataSize() const { 256 return SmallDataThreshold; 257 } 258 259 /// Descends any type down to "elementary" components, 260 /// discovering the smallest addressable one. 261 /// If zero is returned, declaration will not be modified. 262 unsigned HexagonTargetObjectFile::getSmallestAddressableSize(const Type *Ty, 263 const GlobalValue *GV, const TargetMachine &TM) const { 264 // Assign the smallest element access size to the highest 265 // value which assembler can handle. 266 unsigned SmallestElement = 8; 267 268 if (!Ty) 269 return 0; 270 switch (Ty->getTypeID()) { 271 case Type::StructTyID: { 272 const StructType *STy = cast<const StructType>(Ty); 273 for (auto &E : STy->elements()) { 274 unsigned AtomicSize = getSmallestAddressableSize(E, GV, TM); 275 if (AtomicSize < SmallestElement) 276 SmallestElement = AtomicSize; 277 } 278 return (STy->getNumElements() == 0) ? 0 : SmallestElement; 279 } 280 case Type::ArrayTyID: { 281 const ArrayType *ATy = cast<const ArrayType>(Ty); 282 return getSmallestAddressableSize(ATy->getElementType(), GV, TM); 283 } 284 case Type::VectorTyID: { 285 const VectorType *PTy = cast<const VectorType>(Ty); 286 return getSmallestAddressableSize(PTy->getElementType(), GV, TM); 287 } 288 case Type::PointerTyID: 289 case Type::HalfTyID: 290 case Type::FloatTyID: 291 case Type::DoubleTyID: 292 case Type::IntegerTyID: { 293 const DataLayout &DL = GV->getParent()->getDataLayout(); 294 // It is unfortunate that DL's function take non-const Type*. 295 return DL.getTypeAllocSize(const_cast<Type*>(Ty)); 296 } 297 case Type::FunctionTyID: 298 case Type::VoidTyID: 299 case Type::X86_FP80TyID: 300 case Type::FP128TyID: 301 case Type::PPC_FP128TyID: 302 case Type::LabelTyID: 303 case Type::MetadataTyID: 304 case Type::X86_MMXTyID: 305 case Type::TokenTyID: 306 return 0; 307 } 308 309 return 0; 310 } 311 312 MCSection *HexagonTargetObjectFile::selectSmallSectionForGlobal( 313 const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const { 314 const Type *GTy = GO->getType()->getElementType(); 315 unsigned Size = getSmallestAddressableSize(GTy, GO, TM); 316 317 // If we have -ffunction-section or -fdata-section then we should emit the 318 // global value to a unique section specifically for it... even for sdata. 319 bool EmitUniquedSection = TM.getDataSections(); 320 321 TRACE("Small data. Size(" << Size << ")"); 322 // Handle Small Section classification here. 323 if (Kind.isBSS() || Kind.isBSSLocal()) { 324 // If -mno-sort-sda is not set, find out smallest accessible entity in 325 // declaration and add it to the section name string. 326 // Note. It does not track the actual usage of the value, only its de- 327 // claration. Also, compiler adds explicit pad fields to some struct 328 // declarations - they are currently counted towards smallest addres- 329 // sable entity. 330 if (NoSmallDataSorting) { 331 TRACE(" default sbss\n"); 332 return SmallBSSSection; 333 } 334 335 StringRef Prefix(".sbss"); 336 SmallString<128> Name(Prefix); 337 Name.append(getSectionSuffixForSize(Size)); 338 339 if (EmitUniquedSection) { 340 Name.append("."); 341 Name.append(GO->getName()); 342 } 343 TRACE(" unique sbss(" << Name << ")\n"); 344 return getContext().getELFSection(Name.str(), ELF::SHT_NOBITS, 345 ELF::SHF_WRITE | ELF::SHF_ALLOC | ELF::SHF_HEX_GPREL); 346 } 347 348 if (Kind.isCommon()) { 349 // This is purely for LTO+Linker Script because commons don't really have a 350 // section. However, the BitcodeSectionWriter pass will query for the 351 // sections of commons (and the linker expects us to know their section) so 352 // we'll return one here. 353 if (NoSmallDataSorting) 354 return BSSSection; 355 356 Twine Name = Twine(".scommon") + getSectionSuffixForSize(Size); 357 TRACE(" small COMMON (" << Name << ")\n"); 358 359 return getContext().getELFSection(Name.str(), ELF::SHT_NOBITS, 360 ELF::SHF_WRITE | ELF::SHF_ALLOC | 361 ELF::SHF_HEX_GPREL); 362 } 363 364 // We could have changed sdata object to a constant... in this 365 // case the Kind could be wrong for it. 366 if (Kind.isMergeableConst()) { 367 TRACE(" const_object_as_data "); 368 const GlobalVariable *GVar = dyn_cast<GlobalVariable>(GO); 369 if (GVar->hasSection() && isSmallDataSection(GVar->getSection())) 370 Kind = SectionKind::getData(); 371 } 372 373 if (Kind.isData()) { 374 if (NoSmallDataSorting) { 375 TRACE(" default sdata\n"); 376 return SmallDataSection; 377 } 378 379 StringRef Prefix(".sdata"); 380 SmallString<128> Name(Prefix); 381 Name.append(getSectionSuffixForSize(Size)); 382 383 if (EmitUniquedSection) { 384 Name.append("."); 385 Name.append(GO->getName()); 386 } 387 TRACE(" unique sdata(" << Name << ")\n"); 388 return getContext().getELFSection(Name.str(), ELF::SHT_PROGBITS, 389 ELF::SHF_WRITE | ELF::SHF_ALLOC | ELF::SHF_HEX_GPREL); 390 } 391 392 TRACE("default ELF section\n"); 393 // Otherwise, we work the same as ELF. 394 return TargetLoweringObjectFileELF::SelectSectionForGlobal(GO, Kind, TM); 395 } 396