1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2025-01-31 12:41:49 +01:00

[XCOFF][AIX] Handle llvm.used and llvm.compiler.used global array

For now, just return and do nothing when we see llvm.used and
llvm.compiler.used global array.
Hopefully, we could come up with a good solution later to prevent
linker from eliminating symbols in llvm.used array.

Reviewed By: DiggerLin, daltenty

Differential Revision: https://reviews.llvm.org/D84363
This commit is contained in:
jasonliu 2020-07-27 14:04:59 +00:00
parent c0e6798650
commit f9434ab9b2
2 changed files with 50 additions and 12 deletions

View File

@ -1678,22 +1678,31 @@ void PPCAIXAsmPrinter::ValidateGV(const GlobalVariable *GV) {
report_fatal_error("COMDAT not yet supported by AIX.");
}
static bool isSpecialLLVMGlobalArrayForStaticInit(const GlobalVariable *GV) {
return StringSwitch<bool>(GV->getName())
.Cases("llvm.global_ctors", "llvm.global_dtors", true)
.Default(false);
static bool isSpecialLLVMGlobalArrayToSkip(const GlobalVariable *GV) {
return GV->hasAppendingLinkage() &&
StringSwitch<bool>(GV->getName())
// TODO: Update the handling of global arrays for static init when
// we support the ".ref" directive.
// Otherwise, we can skip these arrays, because the AIX linker
// collects static init functions simply based on their name.
.Cases("llvm.global_ctors", "llvm.global_dtors", true)
// TODO: Linker could still eliminate the GV if we just skip
// handling llvm.used array. Skipping them for now until we or the
// AIX OS team come up with a good solution.
.Case("llvm.used", true)
// It's correct to just skip llvm.compiler.used array here.
.Case("llvm.compiler.used", true)
.Default(false);
}
void PPCAIXAsmPrinter::emitGlobalVariable(const GlobalVariable *GV) {
ValidateGV(GV);
// TODO: Update the handling of global arrays for static init when we support
// the ".ref" directive.
// Otherwise, we can skip these arrays, because the AIX linker collects
// static init functions simply based on their name.
if (isSpecialLLVMGlobalArrayForStaticInit(GV))
if (isSpecialLLVMGlobalArrayToSkip(GV))
return;
assert(!GV->getName().startswith("llvm.") &&
"Unhandled intrinsic global variable.");
ValidateGV(GV);
// Create the symbol, set its storage class.
MCSymbolXCOFF *GVSym = cast<MCSymbolXCOFF>(getSymbol(GV));
GVSym->setStorageClass(
@ -1836,8 +1845,11 @@ bool PPCAIXAsmPrinter::doInitialization(Module &M) {
// We need to know, up front, the alignment of csects for the assembly path,
// because once a .csect directive gets emitted, we could not change the
// alignment value on it.
for (const auto &G : M.globals())
for (const auto &G : M.globals()) {
if (isSpecialLLVMGlobalArrayToSkip(&G))
continue;
setCsectAlignment(&G);
}
for (const auto &F : M)
setCsectAlignment(&F);

View File

@ -0,0 +1,26 @@
;; This test verifies llc on AIX would not crash when llvm.used and
;; llvm.compiler.used is presented in the IR.
; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mtriple powerpc-ibm-aix-xcoff < %s | \
; RUN: FileCheck %s
; RUN: llc -verify-machineinstrs -mcpu=pwr4 -mtriple powerpc64-ibm-aix-xcoff < %s | \
; RUN: FileCheck %s
@keep_this = internal global i32 2, align 4
@keep_this2 = internal global i32 3, align 4
@llvm.used = appending global [1 x i8*] [i8* bitcast (i32* @keep_this to i8*)], section "llvm.metadata"
@llvm.compiler.used = appending global [1 x i8*] [i8* bitcast (i32* @keep_this2 to i8*)], section "llvm.metadata"
; CHECK-NOT: llvm.metadata
; CHECK-NOT: llvm.used
; CHECK-NOT: llvm.compiler.used
; CHECK: .lglobl keep_this
; CHECK: keep_this:
; CHECK: .lglobl keep_this2
; CHECK: keep_this2:
; CHECK-NOT: llvm.metadata
; CHECK-NOT: llvm.used
; CHECK-NOT: llvm.compiler.used