[llvm] Do not generate the special .ref for zero-sized sections (PR #66805)

Wael Yehia via llvm-commits llvm-commits at lists.llvm.org
Wed Sep 27 21:50:37 PDT 2023


https://github.com/w2yehia updated https://github.com/llvm/llvm-project/pull/66805

>From c205629c44a9bb27fdcac54a9f22bfd42b9353d1 Mon Sep 17 00:00:00 2001
From: Wael Yehia <wyehia at ca.ibm.com>
Date: Tue, 19 Sep 2023 13:49:39 -0400
Subject: [PATCH 1/2] Do not generate the special .ref for zero-sized sections

---
 llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp | 26 ++++++++++++++++++-----
 1 file changed, 21 insertions(+), 5 deletions(-)

diff --git a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
index 4b97e3e1a09152f..826cfd4caa066ce 100644
--- a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
+++ b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
@@ -280,7 +280,7 @@ class PPCAIXAsmPrinter : public PPCAsmPrinter {
 
   void emitFunctionBodyEnd() override;
 
-  void emitPGORefs();
+  void emitPGORefs(Module &M);
 
   void emitEndOfAsmFile(Module &) override;
 
@@ -2652,10 +2652,26 @@ void PPCAIXAsmPrinter::emitFunctionEntryLabel() {
         getObjFileLowering().getFunctionEntryPointSymbol(Alias, TM));
 }
 
-void PPCAIXAsmPrinter::emitPGORefs() {
-  if (OutContext.hasXCOFFSection(
+void PPCAIXAsmPrinter::emitPGORefs(Module &M) {
+  if (!OutContext.hasXCOFFSection(
           "__llvm_prf_cnts",
-          XCOFF::CsectProperties(XCOFF::XMC_RW, XCOFF::XTY_SD))) {
+          XCOFF::CsectProperties(XCOFF::XMC_RW, XCOFF::XTY_SD)))
+    return;
+
+  // An XCOFF .ref directive translates into a relocation entry from the source
+  // (referring) csect to the destination (referred-to) csect. When the source
+  // csect has zero length, the relocation is ambiguous and should not be
+  // generated.
+  bool HasNonZeroLengthPrfCntsSection = false;
+  const DataLayout &DL = M.getDataLayout();
+  for (GlobalVariable &GV : M.globals())
+    if (GV.hasSection() && GV.getSection().equals("__llvm_prf_cnts") &&
+        DL.getTypeAllocSize(GV.getValueType()) > 0) {
+      HasNonZeroLengthPrfCntsSection = true;
+      break;
+    }
+
+  if (HasNonZeroLengthPrfCntsSection) {
     MCSection *CntsSection = OutContext.getXCOFFSection(
         "__llvm_prf_cnts", SectionKind::getData(),
         XCOFF::CsectProperties(XCOFF::XMC_RW, XCOFF::XTY_SD),
@@ -2689,7 +2705,7 @@ void PPCAIXAsmPrinter::emitEndOfAsmFile(Module &M) {
   if (M.empty() && TOCDataGlobalVars.empty())
     return;
 
-  emitPGORefs();
+  emitPGORefs(M);
 
   // Switch to section to emit TOC base.
   OutStreamer->switchSection(getObjFileLowering().getTOCBaseSection());

>From 0bbcbf18624562f09a3b25981cf6bb48e818d9d4 Mon Sep 17 00:00:00 2001
From: Wael Yehia <wyehia at ca.ibm.com>
Date: Thu, 28 Sep 2023 04:50:05 +0000
Subject: [PATCH 2/2] add tests and improve comment

---
 llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp     | 10 ++-
 .../test/CodeGen/PowerPC/pgo-ref-directive.ll | 75 +++++++++++++++++++
 2 files changed, 81 insertions(+), 4 deletions(-)

diff --git a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
index 826cfd4caa066ce..4f15ba497d84c45 100644
--- a/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
+++ b/llvm/lib/Target/PowerPC/PPCAsmPrinter.cpp
@@ -2658,10 +2658,12 @@ void PPCAIXAsmPrinter::emitPGORefs(Module &M) {
           XCOFF::CsectProperties(XCOFF::XMC_RW, XCOFF::XTY_SD)))
     return;
 
-  // An XCOFF .ref directive translates into a relocation entry from the source
-  // (referring) csect to the destination (referred-to) csect. When the source
-  // csect has zero length, the relocation is ambiguous and should not be
-  // generated.
+  // When inside a csect `foo`, a .ref directive referring to a csect `bar`
+  // translates into a relocation entry from `foo` to` bar`. The referring
+  // csect, `foo`, is identified by its address.  If multiple csects have the
+  // same address (because one or more of them are zero-length), the referring
+  // csect cannot be determined. Hence, we don't generate the .ref directives
+  // if `__llvm_prf_cnts` is an empty section.
   bool HasNonZeroLengthPrfCntsSection = false;
   const DataLayout &DL = M.getDataLayout();
   for (GlobalVariable &GV : M.globals())
diff --git a/llvm/test/CodeGen/PowerPC/pgo-ref-directive.ll b/llvm/test/CodeGen/PowerPC/pgo-ref-directive.ll
index 32aa95d7de6c82a..480b44caaded7a5 100644
--- a/llvm/test/CodeGen/PowerPC/pgo-ref-directive.ll
+++ b/llvm/test/CodeGen/PowerPC/pgo-ref-directive.ll
@@ -18,6 +18,24 @@
 ; RUN:     -xcoff-traceback-table=false --filetype=obj < %t/with-vnds.ll -o %t/with-vnds.o
 ; RUN: llvm-objdump %t/with-vnds.o -tr | FileCheck %s --check-prefix=WITHVNDS-OBJ
 
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false < %t/zero-size-cnts-section.ll | FileCheck %s --check-prefixes=ZERO-SIZE-CNTS
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false --filetype=obj < %t/zero-size-cnts-section.ll -o %t/zero-size-cnts-section.o
+; RUN: llvm-objdump %t/zero-size-cnts-section.o -tr | FileCheck %s --check-prefix=ZERO-SIZE-CNTS-OBJ
+
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false < %t/zero-size-other-section.ll | FileCheck %s --check-prefixes=ZERO-SIZE-OTHER
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc64-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false < %t/zero-size-other-section.ll | FileCheck %s --check-prefixes=ZERO-SIZE-OTHER
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false --filetype=obj < %t/zero-size-other-section.ll -o %t/zero-size-other-section.o
+; RUN: llvm-objdump %t/zero-size-other-section.o -tr | FileCheck %s --check-prefix=ZERO-SIZE-OTHER-OBJ
+; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mattr=-altivec -mtriple powerpc64-ibm-aix-xcoff \
+; RUN:     -xcoff-traceback-table=false --filetype=obj < %t/zero-size-other-section.ll -o %t/zero-size-other-section.o
+; RUN: llvm-objdump %t/zero-size-other-section.o -tr | FileCheck %s --check-prefix=ZERO-SIZE-OTHER-OBJ
+
+
 ;--- no-ref.ll
 ; The absence of a __llvm_prf_cnts section should stop generating the .refs.
 ;
@@ -120,3 +138,60 @@ entry:
 ; WITHVNDS-OBJ-NEXT: 00000000 R_REF                    __llvm_prf_vnds
 ; WITHVNDS-OBJ-NEXT: 00000100 R_POS                    .main
 ; WITHVNDS-OBJ-NEXT: 00000104 R_POS                    TOC
+
+;--- zero-size-cnts-section.ll
+; If __llvm_prf_cnts is of zero size, do not generate the .ref directive.
+; The size of the other sections does not matter.
+
+ at dummy_cnts = private global [0 x i32] zeroinitializer, section "__llvm_prf_cnts", align 4
+ at dummy_data = private global [1 x i64] zeroinitializer, section "__llvm_prf_data", align 8
+ at dummy_name = private constant [0 x i32] zeroinitializer, section "__llvm_prf_names", align 4
+
+ at llvm.used = appending global [3 x ptr]
+  [ptr @dummy_cnts,
+   ptr @dummy_data,
+   ptr @dummy_name], section "llvm.metadata"
+
+define i32 @main() #0 {
+entry:
+  ret i32 1
+}
+
+; ZERO-SIZE-CNTS-NOT: .ref __llvm_prf_data[RW]
+; ZERO-SIZE-CNTS-NOT: .ref __llvm_prf_names[RO]
+; ZERO-SIZE-CNTS-NOT: .ref __llvm_prf_vnds
+
+; ZERO-SIZE-CNTS-OBJ-NOT: R_REF  __llvm_prf_data
+; ZERO-SIZE-CNTS-OBJ-NOT: R_REF  __llvm_prf_names
+; ZERO-SIZE-CNTS-OBJ-NOT: R_REF  __llvm_prf_vnds
+
+;--- zero-size-other-section.ll
+; If __llvm_prf_cnts is of non-zero size, generate the .ref directive even if other sections
+; are zero-sized;
+
+ at __profc_main = private global [1 x i64] zeroinitializer, section "__llvm_prf_cnts", align 8
+ at __profd_main = private global [0 x i64] zeroinitializer, section "__llvm_prf_data", align 8
+ at __llvm_prf_nm = private constant [0 x i8] zeroinitializer, section "__llvm_prf_names", align 1
+ at __llvm_prf_vnodes = private global [0 x { i64, i64, ptr }] zeroinitializer, section "__llvm_prf_vnds"
+
+ at llvm.used = appending global [4 x ptr]
+  [ptr @__profc_main,
+   ptr @__profd_main,
+   ptr @__llvm_prf_nm,
+   ptr @__llvm_prf_vnodes], section "llvm.metadata"
+
+define i32 @main() #0 {
+entry:
+  ret i32 1
+}
+
+; ZERO-SIZE-OTHER:      .csect __llvm_prf_cnts[RW],3
+; ZERO-SIZE-OTHER:      .csect __llvm_prf_cnts[RW],3
+; ZERO-SIZE-OTHER-NEXT: .ref __llvm_prf_data[RW]
+; ZERO-SIZE-OTHER-NEXT: .ref __llvm_prf_names[RO]
+; ZERO-SIZE-OTHER-NEXT: .ref __llvm_prf_vnds[RW]
+
+; ZERO-SIZE-OTHER-OBJ:      R_REF __llvm_prf_data
+; ZERO-SIZE-OTHER-OBJ-NEXT: R_REF __llvm_prf_names
+; ZERO-SIZE-OTHER-OBJ-NEXT: R_REF __llvm_prf_vnds
+



More information about the llvm-commits mailing list