[llvm] 0dc0572 - [XCOFF][AIX] Differentiate usage of label symbol and csect symbol

David Tenty via llvm-commits llvm-commits at lists.llvm.org
Fri Nov 8 06:30:42 PST 2019


Author: Jason Liu
Date: 2019-11-08T09:30:10-05:00
New Revision: 0dc0572b48ed889e6f750fd65b876a0420805377

URL: https://github.com/llvm/llvm-project/commit/0dc0572b48ed889e6f750fd65b876a0420805377
DIFF: https://github.com/llvm/llvm-project/commit/0dc0572b48ed889e6f750fd65b876a0420805377.diff

LOG: [XCOFF][AIX] Differentiate usage of label symbol and csect symbol

Summary:
 We are using symbols to represent label and csect interchangeably before, and that could be a problem.
There are cases we would need to add storage mapping class to the symbol if that symbol is actually the name of a csect, but it's hard for us to figure out whether that symbol is a label or csect.

This patch intend to do the following:
    1. Construct a QualName (A name include the storage mapping class)
       MCSymbolXCOFF for every MCSectionXCOFF.
    2. Keep a pointer to that QualName inside of MCSectionXCOFF.
    3. Use that QualName whenever we need a symbol refers to that
       MCSectionXCOFF.
    4. Adapt the snowball effect from the above changes in
       XCOFFObjectWriter.cpp.

Reviewers: xingxue, DiggerLin, sfertile, daltenty, hubert.reinterpretcast

Reviewed By: DiggerLin, daltenty

Subscribers: wuzish, nemanjai, mgorny, hiraditya, kbarton, jsji, llvm-commits

Tags: #llvm

Differential Revision: https://reviews.llvm.org/D69633

Added: 
    llvm/lib/BinaryFormat/XCOFF.cpp

Modified: 
    llvm/include/llvm/BinaryFormat/XCOFF.h
    llvm/include/llvm/MC/MCAsmInfo.h
    llvm/include/llvm/MC/MCAsmInfoXCOFF.h
    llvm/include/llvm/MC/MCSectionXCOFF.h
    llvm/include/llvm/MC/MCStreamer.h
    llvm/include/llvm/MC/MCXCOFFStreamer.h
    llvm/lib/BinaryFormat/CMakeLists.txt
    llvm/lib/MC/MCAsmInfo.cpp
    llvm/lib/MC/MCAsmInfoXCOFF.cpp
    llvm/lib/MC/MCAsmStreamer.cpp
    llvm/lib/MC/MCContext.cpp
    llvm/lib/MC/MCSectionXCOFF.cpp
    llvm/lib/MC/MCStreamer.cpp
    llvm/lib/MC/MCXCOFFStreamer.cpp
    llvm/lib/MC/XCOFFObjectWriter.cpp
    llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
    llvm/test/CodeGen/PowerPC/aix-xcoff-data.ll
    llvm/test/CodeGen/PowerPC/aix-xcoff-lcomm.ll

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/BinaryFormat/XCOFF.h b/llvm/include/llvm/BinaryFormat/XCOFF.h
index 20a0f446272f..b6c3aaa51fc4 100644
--- a/llvm/include/llvm/BinaryFormat/XCOFF.h
+++ b/llvm/include/llvm/BinaryFormat/XCOFF.h
@@ -13,6 +13,7 @@
 #ifndef LLVM_BINARYFORMAT_XCOFF_H
 #define LLVM_BINARYFORMAT_XCOFF_H
 
+#include "llvm/ADT/StringRef.h"
 #include <cstdint>
 
 namespace llvm {
@@ -251,6 +252,8 @@ enum CFileCpuId : uint8_t {
   TCPU_970 = 19   ///< PPC970 - PowerPC 64-bit architecture.
 };
 
+StringRef getMappingClassString(XCOFF::StorageMappingClass SMC);
+
 } // end namespace XCOFF
 } // end namespace llvm
 

diff  --git a/llvm/include/llvm/MC/MCAsmInfo.h b/llvm/include/llvm/MC/MCAsmInfo.h
index 3261c483e0d8..589f1dfe90b8 100644
--- a/llvm/include/llvm/MC/MCAsmInfo.h
+++ b/llvm/include/llvm/MC/MCAsmInfo.h
@@ -454,6 +454,9 @@ class MCAsmInfo {
                                             unsigned Encoding,
                                             MCStreamer &Streamer) const;
 
+  /// Return true if C is an acceptable character inside a symbol name.
+  virtual bool isAcceptableChar(char C) const;
+
   /// Return true if the identifier \p Name does not need quotes to be
   /// syntactically correct.
   virtual bool isValidUnquotedName(StringRef Name) const;

diff  --git a/llvm/include/llvm/MC/MCAsmInfoXCOFF.h b/llvm/include/llvm/MC/MCAsmInfoXCOFF.h
index 4a3bacc954e0..5483899d5875 100644
--- a/llvm/include/llvm/MC/MCAsmInfoXCOFF.h
+++ b/llvm/include/llvm/MC/MCAsmInfoXCOFF.h
@@ -20,9 +20,9 @@ class MCAsmInfoXCOFF : public MCAsmInfo {
   MCAsmInfoXCOFF();
 
 public:
-  // Return true only when the identifier Name does not need quotes to be
-  // syntactically correct for XCOFF.
-  bool isValidUnquotedName(StringRef Name) const override;
+  // Return true only when C is an acceptable character inside a
+  // MCSymbolXCOFF.
+  bool isAcceptableChar(char C) const override;
 };
 
 } // end namespace llvm

diff  --git a/llvm/include/llvm/MC/MCSectionXCOFF.h b/llvm/include/llvm/MC/MCSectionXCOFF.h
index ee302ed5ecec..604f17d9b136 100644
--- a/llvm/include/llvm/MC/MCSectionXCOFF.h
+++ b/llvm/include/llvm/MC/MCSectionXCOFF.h
@@ -16,11 +16,10 @@
 #include "llvm/ADT/Twine.h"
 #include "llvm/BinaryFormat/XCOFF.h"
 #include "llvm/MC/MCSection.h"
+#include "llvm/MC/MCSymbolXCOFF.h"
 
 namespace llvm {
 
-class MCSymbol;
-
 // This class represents an XCOFF `Control Section`, more commonly referred to
 // as a csect. A csect represents the smallest possible unit of data/code which
 // will be relocated as a single block. A csect can either be:
@@ -38,14 +37,18 @@ class MCSectionXCOFF final : public MCSection {
   XCOFF::StorageMappingClass MappingClass;
   XCOFF::SymbolType Type;
   XCOFF::StorageClass StorageClass;
+  MCSymbolXCOFF *const QualName;
 
   MCSectionXCOFF(StringRef Section, XCOFF::StorageMappingClass SMC,
                  XCOFF::SymbolType ST, XCOFF::StorageClass SC, SectionKind K,
-                 MCSymbol *Begin)
+                 MCSymbolXCOFF *QualName, MCSymbol *Begin)
       : MCSection(SV_XCOFF, K, Begin), Name(Section), MappingClass(SMC),
-        Type(ST), StorageClass(SC) {
+        Type(ST), StorageClass(SC), QualName(QualName) {
     assert((ST == XCOFF::XTY_SD || ST == XCOFF::XTY_CM) &&
            "Invalid or unhandled type for csect.");
+    assert(QualName != nullptr && "QualName is needed.");
+    QualName->setStorageClass(SC);
+    QualName->setContainingCsect(this);
   }
 
 public:
@@ -59,6 +62,7 @@ class MCSectionXCOFF final : public MCSection {
   XCOFF::StorageMappingClass getMappingClass() const { return MappingClass; }
   XCOFF::StorageClass getStorageClass() const { return StorageClass; }
   XCOFF::SymbolType getCSectType() const { return Type; }
+  MCSymbolXCOFF *getQualNameSymbol() const { return QualName; }
 
   void PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T,
                             raw_ostream &OS,

diff  --git a/llvm/include/llvm/MC/MCStreamer.h b/llvm/include/llvm/MC/MCStreamer.h
index 6b48580ae57c..bfe80b777e00 100644
--- a/llvm/include/llvm/MC/MCStreamer.h
+++ b/llvm/include/llvm/MC/MCStreamer.h
@@ -546,11 +546,13 @@ class MCStreamer {
 
   /// Emits an lcomm directive with XCOFF csect information.
   ///
-  /// \param Symbol - The symbol we are emiting.
+  /// \param LabelSym - Label on the block of storage.
   /// \param Size - The size of the block of storage.
-  /// \param ByteAlignment - The alignment of the symbol in bytes. Must be a power
-  /// of 2.
-  virtual void EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
+  /// \param CsectSym - Csect name for the block of storage.
+  /// \param ByteAlignment - The alignment of the symbol in bytes. Must be a
+  /// power of 2.
+  virtual void EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym, uint64_t Size,
+                                          MCSymbol *CsectSym,
                                           unsigned ByteAlignment);
 
   /// Emit an ELF .size directive.

diff  --git a/llvm/include/llvm/MC/MCXCOFFStreamer.h b/llvm/include/llvm/MC/MCXCOFFStreamer.h
index b13b0031d18e..f6f8e56977d3 100644
--- a/llvm/include/llvm/MC/MCXCOFFStreamer.h
+++ b/llvm/include/llvm/MC/MCXCOFFStreamer.h
@@ -26,7 +26,8 @@ class MCXCOFFStreamer : public MCObjectStreamer {
                     uint64_t Size = 0, unsigned ByteAlignment = 0,
                     SMLoc Loc = SMLoc()) override;
   void EmitInstToData(const MCInst &Inst, const MCSubtargetInfo &) override;
-  void EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
+  void EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym, uint64_t Size,
+                                  MCSymbol *CsectSym,
                                   unsigned ByteAlign) override;
 };
 

diff  --git a/llvm/lib/BinaryFormat/CMakeLists.txt b/llvm/lib/BinaryFormat/CMakeLists.txt
index 5d792a6abca5..f8042efd1e70 100644
--- a/llvm/lib/BinaryFormat/CMakeLists.txt
+++ b/llvm/lib/BinaryFormat/CMakeLists.txt
@@ -8,6 +8,7 @@ add_llvm_library(LLVMBinaryFormat
   MsgPackReader.cpp
   MsgPackWriter.cpp
   Wasm.cpp
+  XCOFF.cpp
 
   ADDITIONAL_HEADER_DIRS
   ${LLVM_MAIN_INCLUDE_DIR}/llvm/BinaryFormat

diff  --git a/llvm/lib/BinaryFormat/XCOFF.cpp b/llvm/lib/BinaryFormat/XCOFF.cpp
new file mode 100644
index 000000000000..6613b6329c13
--- /dev/null
+++ b/llvm/lib/BinaryFormat/XCOFF.cpp
@@ -0,0 +1,28 @@
+//===-- llvm/BinaryFormat/XCOFF.cpp - The XCOFF file format -----*- C++/-*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm/BinaryFormat/XCOFF.h"
+
+using namespace llvm;
+
+StringRef XCOFF::getMappingClassString(XCOFF::StorageMappingClass SMC) {
+  switch (SMC) {
+  case XCOFF::XMC_DS:
+    return "DS";
+  case XCOFF::XMC_RW:
+    return "RW";
+  case XCOFF::XMC_PR:
+    return "PR";
+  case XCOFF::XMC_TC0:
+    return "TC0";
+  case XCOFF::XMC_BS:
+    return "BS";
+  default:
+    report_fatal_error("Unhandled storage-mapping class.");
+  }
+}

diff  --git a/llvm/lib/MC/MCAsmInfo.cpp b/llvm/lib/MC/MCAsmInfo.cpp
index 71e51e320f8b..420dbaa80ae9 100644
--- a/llvm/lib/MC/MCAsmInfo.cpp
+++ b/llvm/lib/MC/MCAsmInfo.cpp
@@ -100,7 +100,7 @@ MCAsmInfo::getExprForFDESymbol(const MCSymbol *Sym,
   return MCBinaryExpr::createSub(Res, PC, Context);
 }
 
-static bool isAcceptableChar(char C) {
+bool MCAsmInfo::isAcceptableChar(char C) const {
   return (C >= 'a' && C <= 'z') || (C >= 'A' && C <= 'Z') ||
          (C >= '0' && C <= '9') || C == '_' || C == '$' || C == '.' || C == '@';
 }

diff  --git a/llvm/lib/MC/MCAsmInfoXCOFF.cpp b/llvm/lib/MC/MCAsmInfoXCOFF.cpp
index 65fe8848e20f..c51cdff59fa0 100644
--- a/llvm/lib/MC/MCAsmInfoXCOFF.cpp
+++ b/llvm/lib/MC/MCAsmInfoXCOFF.cpp
@@ -26,10 +26,11 @@ MCAsmInfoXCOFF::MCAsmInfoXCOFF() {
   SupportsQuotedNames = false;
 }
 
-bool MCAsmInfoXCOFF::isValidUnquotedName(StringRef Name) const {
-  // FIXME: Remove this function when we stop using "TOC[TC0]" as a symbol name.
-  if (Name.equals("TOC[TC0]"))
+bool MCAsmInfoXCOFF::isAcceptableChar(char C) const {
+  // QualName is allowed for a MCSymbolXCOFF, and
+  // QualName contains '[' and ']'.
+  if (C == '[' || C == ']')
     return true;
 
-  return MCAsmInfo::isValidUnquotedName(Name);
+  return MCAsmInfo::isAcceptableChar(C);
 }

diff  --git a/llvm/lib/MC/MCAsmStreamer.cpp b/llvm/lib/MC/MCAsmStreamer.cpp
index 2d9c2cb21255..3fe401de35d9 100644
--- a/llvm/lib/MC/MCAsmStreamer.cpp
+++ b/llvm/lib/MC/MCAsmStreamer.cpp
@@ -164,7 +164,8 @@ class MCAsmStreamer final : public MCStreamer {
   void EmitCOFFSectionIndex(MCSymbol const *Symbol) override;
   void EmitCOFFSecRel32(MCSymbol const *Symbol, uint64_t Offset) override;
   void EmitCOFFImgRel32(MCSymbol const *Symbol, int64_t Offset) override;
-  void EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
+  void EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym, uint64_t Size,
+                                  MCSymbol *CsectSym,
                                   unsigned ByteAlign) override;
   void emitELFSize(MCSymbol *Symbol, const MCExpr *Value) override;
   void EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
@@ -765,16 +766,18 @@ void MCAsmStreamer::EmitCOFFImgRel32(MCSymbol const *Symbol, int64_t Offset) {
 // We need an XCOFF-specific version of this directive as the AIX syntax
 // requires a QualName argument identifying the csect name and storage mapping
 // class to appear before the alignment if we are specifying it.
-void MCAsmStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
+void MCAsmStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym,
+                                               uint64_t Size,
+                                               MCSymbol *CsectSym,
                                                unsigned ByteAlignment) {
   assert(MAI->getLCOMMDirectiveAlignmentType() == LCOMM::Log2Alignment &&
          "We only support writing log base-2 alignment format with XCOFF.");
   assert(isPowerOf2_32(ByteAlignment) && "Alignment must be a power of 2.");
 
   OS << "\t.lcomm\t";
-  Symbol->print(OS, MAI);
-  OS << ',' << Size;
-  OS << ',' << Symbol->getName();
+  LabelSym->print(OS, MAI);
+  OS << ',' << Size << ',';
+  CsectSym->print(OS, MAI);
   OS << ',' << Log2_32(ByteAlignment);
 
   EmitEOL();

diff  --git a/llvm/lib/MC/MCContext.cpp b/llvm/lib/MC/MCContext.cpp
index a69ee19e1a1a..a6417113fd38 100644
--- a/llvm/lib/MC/MCContext.cpp
+++ b/llvm/lib/MC/MCContext.cpp
@@ -15,6 +15,7 @@
 #include "llvm/ADT/Twine.h"
 #include "llvm/BinaryFormat/COFF.h"
 #include "llvm/BinaryFormat/ELF.h"
+#include "llvm/BinaryFormat/XCOFF.h"
 #include "llvm/MC/MCAsmInfo.h"
 #include "llvm/MC/MCCodeView.h"
 #include "llvm/MC/MCDwarf.h"
@@ -550,13 +551,15 @@ MCSectionXCOFF *MCContext::getXCOFFSection(StringRef Section,
 
   // Otherwise, return a new section.
   StringRef CachedName = Entry.first.SectionName;
+  MCSymbol *QualName = getOrCreateSymbol(
+      CachedName + "[" + XCOFF::getMappingClassString(SMC) + "]");
 
   MCSymbol *Begin = nullptr;
   if (BeginSymName)
     Begin = createTempSymbol(BeginSymName, false);
 
-  MCSectionXCOFF *Result = new (XCOFFAllocator.Allocate())
-      MCSectionXCOFF(CachedName, SMC, Type, SC, Kind, Begin);
+  MCSectionXCOFF *Result = new (XCOFFAllocator.Allocate()) MCSectionXCOFF(
+      CachedName, SMC, Type, SC, Kind, cast<MCSymbolXCOFF>(QualName), Begin);
   Entry.second = Result;
 
   auto *F = new MCDataFragment();

diff  --git a/llvm/lib/MC/MCSectionXCOFF.cpp b/llvm/lib/MC/MCSectionXCOFF.cpp
index d52959f15f92..d00e93228970 100644
--- a/llvm/lib/MC/MCSectionXCOFF.cpp
+++ b/llvm/lib/MC/MCSectionXCOFF.cpp
@@ -15,18 +15,6 @@ using namespace llvm;
 
 MCSectionXCOFF::~MCSectionXCOFF() = default;
 
-static StringRef getMappingClassString(XCOFF::StorageMappingClass SMC) {
-  switch (SMC) {
-  case XCOFF::XMC_DS:
-    return "DS";
-  case XCOFF::XMC_RW:
-    return "RW";
-  case XCOFF::XMC_PR:
-    return "PR";
-  default:
-    report_fatal_error("Unhandled storage-mapping class.");
-  }
-}
 
 void MCSectionXCOFF::PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T,
                                           raw_ostream &OS,
@@ -35,9 +23,7 @@ void MCSectionXCOFF::PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T,
     if (getMappingClass() != XCOFF::XMC_PR)
       report_fatal_error("Unhandled storage-mapping class for .text csect");
 
-    OS << "\t.csect " << getSectionName() << "["
-       << getMappingClassString(getMappingClass())
-       << "]" << '\n';
+    OS << "\t.csect " << QualName->getName() << '\n';
     return;
   }
 
@@ -45,8 +31,7 @@ void MCSectionXCOFF::PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T,
     switch (getMappingClass()) {
     case XCOFF::XMC_RW:
     case XCOFF::XMC_DS:
-      OS << "\t.csect " << getSectionName() << "["
-         << getMappingClassString(getMappingClass()) << "]" << '\n';
+      OS << "\t.csect " << QualName->getName() << '\n';
       break;
     case XCOFF::XMC_TC0:
       OS << "\t.toc\n";

diff  --git a/llvm/lib/MC/MCStreamer.cpp b/llvm/lib/MC/MCStreamer.cpp
index b8278cb11079..c48ee76b3fc6 100644
--- a/llvm/lib/MC/MCStreamer.cpp
+++ b/llvm/lib/MC/MCStreamer.cpp
@@ -1063,7 +1063,8 @@ void MCStreamer::EmitCOFFSymbolStorageClass(int StorageClass) {
 void MCStreamer::EmitCOFFSymbolType(int Type) {
   llvm_unreachable("this directive only supported on COFF targets");
 }
-void MCStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
+void MCStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym, uint64_t Size,
+                                            MCSymbol *CsectSym,
                                             unsigned ByteAlign) {
   llvm_unreachable("this directive only supported on XCOFF targets");
 }

diff  --git a/llvm/lib/MC/MCXCOFFStreamer.cpp b/llvm/lib/MC/MCXCOFFStreamer.cpp
index 50937d6adc0c..c40a067e93e1 100644
--- a/llvm/lib/MC/MCXCOFFStreamer.cpp
+++ b/llvm/lib/MC/MCXCOFFStreamer.cpp
@@ -94,8 +94,9 @@ MCStreamer *llvm::createXCOFFStreamer(MCContext &Context,
   return S;
 }
 
-void MCXCOFFStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *Symbol,
+void MCXCOFFStreamer::EmitXCOFFLocalCommonSymbol(MCSymbol *LabelSym,
                                                  uint64_t Size,
+                                                 MCSymbol *CsectSym,
                                                  unsigned ByteAlignment) {
-  EmitCommonSymbol(Symbol, Size, ByteAlignment);
+  EmitCommonSymbol(CsectSym, Size, ByteAlignment);
 }

diff  --git a/llvm/lib/MC/XCOFFObjectWriter.cpp b/llvm/lib/MC/XCOFFObjectWriter.cpp
index d8f9e0b593bf..cec74ee76c3c 100644
--- a/llvm/lib/MC/XCOFFObjectWriter.cpp
+++ b/llvm/lib/MC/XCOFFObjectWriter.cpp
@@ -78,15 +78,7 @@ struct ControlSection {
 // (approximately) the same storage mapping class. For example all the csects
 // with a storage mapping class of `xmc_pr` will get placed into the same
 // container.
-struct CsectGroup {
-  enum LabelDefinitionSupport : bool {
-    LabelDefSupported = true,
-    LabelDefUnsupported = false
-  };
-
-  const LabelDefinitionSupport SupportLabelDef;
-  std::deque<ControlSection> Csects;
-};
+using CsectGroup = std::deque<ControlSection>;
 
 using CsectGroups = std::deque<CsectGroup *>;
 
@@ -132,7 +124,7 @@ struct Section {
     Index = UninitializedIndex;
     // Clear any csects we have stored.
     for (auto *Group : Groups)
-      Group->Csects.clear();
+      Group->clear();
   }
 
   Section(const char *N, XCOFF::SectionTypeFlags Flags, bool IsVirtual,
@@ -157,9 +149,9 @@ class XCOFFObjectWriter : public MCObjectWriter {
   // CsectGroups. These store the csects which make up 
diff erent parts of
   // the sections. Should have one for each set of csects that get mapped into
   // the same section and get handled in a 'similar' way.
-  CsectGroup ProgramCodeCsects{CsectGroup::LabelDefSupported, {}};
-  CsectGroup DataCsects{CsectGroup::LabelDefSupported, {}};
-  CsectGroup BSSCsects{CsectGroup::LabelDefUnsupported, {}};
+  CsectGroup ProgramCodeCsects;
+  CsectGroup DataCsects;
+  CsectGroup BSSCsects;
 
   // The Predefined sections.
   Section Text;
@@ -294,8 +286,8 @@ void XCOFFObjectWriter::executePostLayoutBinding(MCAssembler &Asm,
       continue;
 
     CsectGroup &Group = getCsectGroup(MCSec);
-    Group.Csects.emplace_back(MCSec);
-    WrapperMap[MCSec] = &Group.Csects.back();
+    Group.emplace_back(MCSec);
+    WrapperMap[MCSec] = &Group.back();
   }
 
   for (const MCSymbol &S : Asm.symbols()) {
@@ -309,6 +301,11 @@ void XCOFFObjectWriter::executePostLayoutBinding(MCAssembler &Asm,
     assert(WrapperMap.find(ContainingCsect) != WrapperMap.end() &&
            "Expected containing csect to exist in map");
 
+    // If the symbol is the Csect itself, we don't need to put the symbol
+    // into Csect's Syms.
+    if (XSym == ContainingCsect->getQualNameSymbol())
+      continue;
+
     // Lookup the containing csect and add the symbol to it.
     WrapperMap[ContainingCsect]->Syms.emplace_back(XSym);
 
@@ -339,7 +336,7 @@ void XCOFFObjectWriter::writeSections(const MCAssembler &Asm,
     assert(CurrentAddressLocation == Section->Address &&
            "We should have no padding between sections.");
     for (const auto *Group : Section->Groups) {
-      for (const auto &Csect : Group->Csects) {
+      for (const auto &Csect : *Group) {
         if (uint32_t PaddingSize = Csect.Address - CurrentAddressLocation)
           W.OS.write_zeros(PaddingSize);
         Asm.writeSectionData(W.OS, Csect.MCCsect, Layout);
@@ -527,20 +524,14 @@ void XCOFFObjectWriter::writeSymbolTable(const MCAsmLayout &Layout) {
       continue;
 
     for (const auto *Group : Section->Groups) {
-      if (Group->Csects.empty())
+      if (Group->empty())
         continue;
 
-      const bool SupportLabelDef = Group->SupportLabelDef;
       const int16_t SectionIndex = Section->Index;
-      for (const auto &Csect : Group->Csects) {
+      for (const auto &Csect : *Group) {
         // Write out the control section first and then each symbol in it.
         writeSymbolTableEntryForControlSection(
             Csect, SectionIndex, Csect.MCCsect->getStorageClass());
-        if (!SupportLabelDef) {
-          assert(Csect.Syms.size() == 1 && "Csect should only contain 1 symbol "
-                                           "which is its label definition.");
-          continue;
-        }
 
         for (const auto Sym : Csect.Syms)
           writeSymbolTableEntryForCsectMemberLabel(
@@ -563,9 +554,8 @@ void XCOFFObjectWriter::assignAddressesAndIndices(const MCAsmLayout &Layout) {
 
   for (auto *Section : Sections) {
     const bool IsEmpty =
-        llvm::all_of(Section->Groups, [](const CsectGroup *Group) {
-          return Group->Csects.empty();
-        });
+        llvm::all_of(Section->Groups,
+                     [](const CsectGroup *Group) { return Group->empty(); });
     if (IsEmpty)
       continue;
 
@@ -576,11 +566,10 @@ void XCOFFObjectWriter::assignAddressesAndIndices(const MCAsmLayout &Layout) {
 
     bool SectionAddressSet = false;
     for (auto *Group : Section->Groups) {
-      if (Group->Csects.empty())
+      if (Group->empty())
         continue;
 
-      const bool SupportLabelDef = Group->SupportLabelDef;
-      for (auto &Csect : Group->Csects) {
+      for (auto &Csect : *Group) {
         const MCSectionXCOFF *MCSec = Csect.MCCsect;
         Csect.Address = alignTo(Address, MCSec->getAlignment());
         Csect.Size = Layout.getSectionAddressSize(MCSec);
@@ -588,10 +577,7 @@ void XCOFFObjectWriter::assignAddressesAndIndices(const MCAsmLayout &Layout) {
         Csect.SymbolTableIndex = SymbolTableIndex;
         // 1 main and 1 auxiliary symbol table entry for the csect.
         SymbolTableIndex += 2;
-
-        if (!SupportLabelDef)
-          continue;
-
+        
         for (auto &Sym : Csect.Syms) {
           Sym.SymbolTableIndex = SymbolTableIndex;
           // 1 main and 1 auxiliary symbol table entry for each contained
@@ -601,7 +587,7 @@ void XCOFFObjectWriter::assignAddressesAndIndices(const MCAsmLayout &Layout) {
       }
 
       if (!SectionAddressSet) {
-        Section->Address = Group->Csects.front().Address;
+        Section->Address = Group->front().Address;
         SectionAddressSet = true;
       }
     }

diff  --git a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
index 66236b72a1a3..49365bcefa0a 100644
--- a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
+++ b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
@@ -1752,15 +1752,15 @@ void PPCAIXAsmPrinter::EmitGlobalVariable(const GlobalVariable *GV) {
                        "not supported yet.");
 
   // Create the containing csect and switch to it.
-  MCSectionXCOFF *CSect = cast<MCSectionXCOFF>(
+  MCSectionXCOFF *Csect = cast<MCSectionXCOFF>(
       getObjFileLowering().SectionForGlobal(GV, GVKind, TM));
-  OutStreamer->SwitchSection(CSect);
+  OutStreamer->SwitchSection(Csect);
 
   // Create the symbol, set its storage class, and emit it.
   MCSymbolXCOFF *GVSym = cast<MCSymbolXCOFF>(getSymbol(GV));
   GVSym->setStorageClass(
       TargetLoweringObjectFileXCOFF::getStorageClassForGlobal(GV));
-  GVSym->setContainingCsect(CSect);
+  GVSym->setContainingCsect(Csect);
 
   const DataLayout &DL = GV->getParent()->getDataLayout();
 
@@ -1771,9 +1771,10 @@ void PPCAIXAsmPrinter::EmitGlobalVariable(const GlobalVariable *GV) {
     uint64_t Size = DL.getTypeAllocSize(GV->getType()->getElementType());
 
     if (GVKind.isBSSLocal())
-      OutStreamer->EmitXCOFFLocalCommonSymbol(GVSym, Size, Align);
+      OutStreamer->EmitXCOFFLocalCommonSymbol(
+          GVSym, Size, Csect->getQualNameSymbol(), Align);
     else
-      OutStreamer->EmitCommonSymbol(GVSym, Size, Align);
+      OutStreamer->EmitCommonSymbol(Csect->getQualNameSymbol(), Size, Align);
     return;
   }
 
@@ -1813,11 +1814,9 @@ void PPCAIXAsmPrinter::EmitEndOfAsmFile(Module &M) {
     return;
 
   // Emit TOC base.
-  MCSymbol *TOCBaseSym = OutContext.getOrCreateSymbol(StringRef("TOC[TC0]"));
   MCSectionXCOFF *TOCBaseSection = OutStreamer->getContext().getXCOFFSection(
       StringRef("TOC"), XCOFF::XMC_TC0, XCOFF::XTY_SD, XCOFF::C_HIDEXT,
       SectionKind::getData());
-  cast<MCSymbolXCOFF>(TOCBaseSym)->setContainingCsect(TOCBaseSection);
   // Switch to section to emit TOC base.
   OutStreamer->SwitchSection(TOCBaseSection);
 }

diff  --git a/llvm/test/CodeGen/PowerPC/aix-xcoff-data.ll b/llvm/test/CodeGen/PowerPC/aix-xcoff-data.ll
index 3e69a586edce..5c8ac0587154 100644
--- a/llvm/test/CodeGen/PowerPC/aix-xcoff-data.ll
+++ b/llvm/test/CodeGen/PowerPC/aix-xcoff-data.ll
@@ -84,13 +84,13 @@
 ; CHECK-NEXT: .llong  4613937818241073152
 ; CHECK-NEXT: .llong  4616189618054758400
 
-; CHECK-NEXT: .comm   a,4,2
-; CHECK-NEXT: .comm   b,8,3
-; CHECK-NEXT: .comm   c,2,1
-; CHECK-NEXT: .comm   d,8,3
-; CHECK-NEXT: .comm   f,4,2
-; CHECK-NEXT: .comm   over_aligned_comm,8,5
-; CHECK-NEXT: .comm   array,33,0
+; CHECK-NEXT: .comm   a[RW],4,2
+; CHECK-NEXT: .comm   b[RW],8,3
+; CHECK-NEXT: .comm   c[RW],2,1
+; CHECK-NEXT: .comm   d[RW],8,3
+; CHECK-NEXT: .comm   f[RW],4,2
+; CHECK-NEXT: .comm   over_aligned_comm[RW],8,5
+; CHECK-NEXT: .comm   array[RW],33,0
 
 ; OBJ:      File: {{.*}}aix-xcoff-data.ll.tmp.o
 ; OBJ-NEXT: Format: aixcoff-rs6000

diff  --git a/llvm/test/CodeGen/PowerPC/aix-xcoff-lcomm.ll b/llvm/test/CodeGen/PowerPC/aix-xcoff-lcomm.ll
index cba713464e04..536229fc8c45 100644
--- a/llvm/test/CodeGen/PowerPC/aix-xcoff-lcomm.ll
+++ b/llvm/test/CodeGen/PowerPC/aix-xcoff-lcomm.ll
@@ -14,9 +14,9 @@
 @b = internal global i64 0, align 8
 @c = internal global i16 0, align 2
 
-; CHECK:      .lcomm a,4,a,2
-; CHECK-NEXT: .lcomm b,8,b,3
-; CHECK-NEXT: .lcomm c,2,c,1
+; CHECK:      .lcomm a,4,a[BS],2
+; CHECK-NEXT: .lcomm b,8,b[BS],3
+; CHECK-NEXT: .lcomm c,2,c[BS],1
 
 ; OBJ:      File: {{.*}}aix-xcoff-lcomm.ll.tmp.o
 ; OBJ-NEXT: Format: aixcoff-rs6000


        


More information about the llvm-commits mailing list