Handle ELF mergeable sections
authorAnton Korobeynikov <asl@math.spbu.ru>
Wed, 9 Jul 2008 13:23:37 +0000 (13:23 +0000)
committerAnton Korobeynikov <asl@math.spbu.ru>
Wed, 9 Jul 2008 13:23:37 +0000 (13:23 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@53306 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/Target/TargetAsmInfo.h
lib/Target/X86/X86TargetAsmInfo.cpp
lib/Target/X86/X86TargetAsmInfo.h

index 6194e163cd5ba3e3983803eea78f717383282006..8d2861f6a673182d56b64017c33e06fd12b74553 100644 (file)
@@ -57,12 +57,12 @@ namespace llvm {
       EntitySize = 0xFF << 24 ///< Entity size for mergeable sections
     };
 
-    static inline unsigned getEntitySize(unsigned flags) {
-      return (flags >> 24) & 0xFF;
+    static inline unsigned getEntitySize(unsigned Flags) {
+      return (Flags >> 24) & 0xFF;
     }
 
-    static inline unsigned setEntitySize(unsigned flags, unsigned size) {
-      return ((flags & ~EntitySize) | ((size & 0xFF) << 24));
+    static inline unsigned setEntitySize(unsigned Flags, unsigned Size) {
+      return ((Flags & ~EntitySize) | ((Size & 0xFF) << 24));
     }
   }
 
index 5e328fb78a36ab288ca5cd71b4b583e7d9b4a63b..1217291a1d8582f2ec44c0f2043cd1ba4a343768 100644 (file)
@@ -341,10 +341,11 @@ X86ELFTargetAsmInfo::SelectSectionForGlobal(const GlobalValue *GV) const {
         // ELF targets usually have BSS sections
         return getBSSSection();
        case SectionKind::ROData:
+        return getReadOnlySection();
        case SectionKind::RODataMergeStr:
+        return MergeableStringSection(GVar);
        case SectionKind::RODataMergeConst:
-        // FIXME: Temporary
-        return getReadOnlySection();
+        return MergeableConstSection(GVar);
        case SectionKind::ThreadData:
         // ELF targets usually support TLS stuff
         return getTLSDataSection();
@@ -358,6 +359,66 @@ X86ELFTargetAsmInfo::SelectSectionForGlobal(const GlobalValue *GV) const {
     assert(0 && "Unsupported global");
 }
 
+std::string
+X86ELFTargetAsmInfo::MergeableConstSection(const GlobalVariable *GV) const {
+  unsigned Flags = SectionFlagsForGlobal(GV, GV->getSection().c_str());
+  unsigned Size = SectionFlags::getEntitySize(Flags);
+
+  // FIXME: string here is temporary, until stuff will fully land in.
+  if (Size)
+    return ".rodata.cst" + utostr(Size);
+  else
+    return getReadOnlySection();
+}
+
+std::string
+X86ELFTargetAsmInfo::MergeableStringSection(const GlobalVariable *GV) const {
+  unsigned Flags = SectionFlagsForGlobal(GV, GV->getSection().c_str());
+  unsigned Size = SectionFlags::getEntitySize(Flags);
+
+  if (Size) {
+    // We also need alignment here
+    const TargetData *TD = X86TM->getTargetData();
+    unsigned Align = TD->getPreferredAlignment(GV);
+    if (Align < Size)
+      Align = Size;
+
+    // FIXME: string here is temporary, until stuff will fully land in.
+    return ".rodata.str" + utostr(Size) + ',' + utostr(Align);
+  } else
+    return getReadOnlySection();
+}
+
+unsigned
+X86ELFTargetAsmInfo::SectionFlagsForGlobal(const GlobalValue *GV,
+                                           const char* name) const {
+  unsigned Flags =
+    TargetAsmInfo::SectionFlagsForGlobal(GV,
+                                         GV->getSection().c_str());
+
+  // If there was decision to put stuff into mergeable section - calculate
+  // entity size
+  if (Flags & SectionFlags::Mergeable) {
+    const TargetData *TD = X86TM->getTargetData();
+    Constant *C = cast<GlobalVariable>(GV)->getInitializer();
+    const Type *Type;
+
+    if (Flags & SectionFlags::Strings) {
+      const ConstantArray *CVA = cast<ConstantArray>(C);
+      Type = CVA->getType()->getElementType();
+    } else
+      Type = C->getType();
+
+    unsigned Size = TD->getABITypeSize(Type);
+    if (Size > 32)
+      Size = 0;
+    Flags = SectionFlags::setEntitySize(Flags, Size);
+  }
+
+  return Flags;
+}
+
+
 std::string X86ELFTargetAsmInfo::PrintSectionFlags(unsigned flags) const {
   std::string Flags = ",\"";
 
index 483b774d6d9d4c2b8ba42276e6052eb093d9cd1f..dd8d3d1afb1aeeca6ca7b02f1efbba88295484f3 100644 (file)
@@ -20,6 +20,7 @@ namespace llvm {
 
   // Forward declaration.
   class X86TargetMachine;
+  class GlobalVariable;
 
   struct X86TargetAsmInfo : public TargetAsmInfo {
     explicit X86TargetAsmInfo(const X86TargetMachine &TM);
@@ -47,7 +48,11 @@ namespace llvm {
                                            bool Global) const;
 
     virtual std::string SelectSectionForGlobal(const GlobalValue *GV) const;
+    virtual unsigned SectionFlagsForGlobal(const GlobalValue *GV,
+                                           const char* name) const;
     virtual std::string PrintSectionFlags(unsigned flags) const;
+    std::string MergeableConstSection(const GlobalVariable *GV) const;
+    std::string MergeableStringSection(const GlobalVariable *GV) const;
   };
 
   struct X86COFFTargetAsmInfo : public X86TargetAsmInfo {