[XCOFF] make related SD symbols as isFunction (#69553)

This will help tools like llvm-symbolizer recognizes more functions.
This commit is contained in:
Chen Zheng 2023-11-26 11:59:09 +08:00 committed by GitHub
parent 3bbed4ee26
commit abc405858d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 96 additions and 24 deletions

View File

@ -853,6 +853,9 @@ public:
xcoff_symbol_iterator(const basic_symbol_iterator &B)
: symbol_iterator(B) {}
xcoff_symbol_iterator(const XCOFFSymbolRef *Symbol)
: symbol_iterator(*Symbol) {}
const XCOFFSymbolRef *operator->() const {
return static_cast<const XCOFFSymbolRef *>(symbol_iterator::operator->());
}

View File

@ -1242,21 +1242,57 @@ Expected<bool> XCOFFSymbolRef::isFunction() const {
const XCOFFCsectAuxRef CsectAuxRef = ExpCsectAuxEnt.get();
// A function definition should be a label definition.
// FIXME: This is not necessarily the case when -ffunction-sections is
// enabled.
if (!CsectAuxRef.isLabel())
if (CsectAuxRef.getStorageMappingClass() != XCOFF::XMC_PR &&
CsectAuxRef.getStorageMappingClass() != XCOFF::XMC_GL)
return false;
if (CsectAuxRef.getStorageMappingClass() != XCOFF::XMC_PR)
// A function definition should not be a common type symbol or an external
// symbol.
if (CsectAuxRef.getSymbolType() == XCOFF::XTY_CM ||
CsectAuxRef.getSymbolType() == XCOFF::XTY_ER)
return false;
const int16_t SectNum = getSectionNumber();
Expected<DataRefImpl> SI = getObject()->getSectionByNum(SectNum);
if (!SI)
return SI.takeError();
// If the next symbol is an XTY_LD type symbol with the same address, this
// XTY_SD symbol is not a function. Otherwise this is a function symbol for
// -ffunction-sections.
if (CsectAuxRef.getSymbolType() == XCOFF::XTY_SD) {
// If this is a csect with size 0, it won't be a function definition.
// This is used to work around the fact that LLVM always generates below
// symbol for -ffunction-sections:
// m 0x00000000 .text 1 unamex **No Symbol**
// a4 0x00000000 0 0 SD PR 0 0
// FIXME: remove or replace this meaningless symbol.
if (getSize() == 0)
return false;
return (getObject()->getSectionFlags(SI.get()) & XCOFF::STYP_TEXT);
xcoff_symbol_iterator NextIt(this);
// If this is the last main symbol table entry, there won't be an XTY_LD
// type symbol below.
if (++NextIt == getObject()->symbol_end())
return true;
if (cantFail(getAddress()) != cantFail(NextIt->getAddress()))
return true;
// Check next symbol is XTY_LD. If so, this symbol is not a function.
Expected<XCOFFCsectAuxRef> NextCsectAuxEnt = NextIt->getXCOFFCsectAuxRef();
if (!NextCsectAuxEnt)
return NextCsectAuxEnt.takeError();
if (NextCsectAuxEnt.get().getSymbolType() == XCOFF::XTY_LD)
return false;
return true;
}
if (CsectAuxRef.getSymbolType() == XCOFF::XTY_LD)
return true;
return createError(
"symbol csect aux entry with index " +
Twine(getObject()->getSymbolIndex(CsectAuxRef.getEntryAddress())) +
" has invalid symbol type " +
Twine::utohexstr(CsectAuxRef.getSymbolType()));
}
bool XCOFFSymbolRef::isCsectSymbol() const {

View File

@ -17,13 +17,13 @@ entry:
ret i32 2
}
; CHECKFS32: 00000000 l .text 00000000 (idx: {{[[:digit:]]*}}) [PR]
; CHECKFS32-NEXT: 00000000 g .text {{([[:xdigit:]]{8})}} (idx: {{[[:digit:]]*}}) .text[PR]
; CHECKFS32-NEXT: {{([[:xdigit:]]{8})}} g .text {{([[:xdigit:]]{8})}} (idx: {{[[:digit:]]*}}) .text2[PR]
; CHECKFS32: 00000000 l .text 00000000 (idx: {{[[:digit:]]*}}) [PR]
; CHECKFS32-NEXT: 00000000 g F .text {{([[:xdigit:]]{8})}} (idx: {{[[:digit:]]*}}) .text[PR]
; CHECKFS32-NEXT: {{([[:xdigit:]]{8})}} g F .text {{([[:xdigit:]]{8})}} (idx: {{[[:digit:]]*}}) .text2[PR]
; CHECKFS64: 0000000000000000 l .text 0000000000000000
; CHECKFS64-NEXT: 0000000000000000 g .text {{([[:xdigit:]]{16})}} (idx: {{[[:digit:]]*}}) .text[PR]
; CHECKFS64-NEXT: {{([[:xdigit:]]{16})}} g .text {{([[:xdigit:]]{16})}} (idx: {{[[:digit:]]*}}) .text2[PR]
; CHECKFS64: 0000000000000000 l .text 0000000000000000
; CHECKFS64-NEXT: 0000000000000000 g F .text {{([[:xdigit:]]{16})}} (idx: {{[[:digit:]]*}}) .text[PR]
; CHECKFS64-NEXT: {{([[:xdigit:]]{16})}} g F .text {{([[:xdigit:]]{16})}} (idx: {{[[:digit:]]*}}) .text2[PR]
; CHECK32: 00000000 l .text {{([[:xdigit:]]{8})}} (idx: {{[[:digit:]]*}}) [PR]
; CHECK32-NEXT: {{([[:xdigit:]]{8})}} g F .text (csect: (idx: {{[[:digit:]]*}}) [PR]) 00000000 (idx: {{[[:digit:]]*}}) .text

View File

@ -117,9 +117,9 @@ entry:
; XCOFF32-NEXT: 00000000 l .text 00000000 (idx: 5) [PR]
; XCOFF32-NEXT: 00000000 g .text 00000019 (idx: 7) .foo[PR]
; XCOFF32-NEXT: 00000000 g F .text (csect: (idx: 7) .foo[PR]) 00000000 (idx: 9) .alias_foo
; XCOFF32-NEXT: 00000020 g .text 00000020 .hidden (idx: 11) .hidden_foo[PR]
; XCOFF32-NEXT: 00000040 g .text 00000059 (idx: 13) .bar[PR]
; XCOFF32-NEXT: 000000c0 l .text 0000002a (idx: 15) .static_overalign_foo[PR]
; XCOFF32-NEXT: 00000020 g F .text 00000020 .hidden (idx: 11) .hidden_foo[PR]
; XCOFF32-NEXT: 00000040 g F .text 00000059 (idx: 13) .bar[PR]
; XCOFF32-NEXT: 000000c0 l F .text 0000002a (idx: 15) .static_overalign_foo[PR]
; XCOFF32-NEXT: 000000ec g O .data 0000000c (idx: 17) foo[DS]
; XCOFF32-NEXT: 000000ec g O .data (csect: (idx: 17) foo[DS]) 00000000 (idx: 19) alias_foo
; XCOFF32-NEXT: 000000f8 g O .data 0000000c .hidden (idx: 21) hidden_foo[DS]
@ -152,9 +152,9 @@ entry:
; XCOFF64-NEXT: 0000000000000000 l .text 0000000000000000 (idx: 5) [PR]
; XCOFF64-NEXT: 0000000000000000 g .text 0000000000000019 (idx: 7) .foo[PR]
; XCOFF64-NEXT: 0000000000000000 g F .text (csect: (idx: 7) .foo[PR]) 0000000000000000 (idx: 9) .alias_foo
; XCOFF64-NEXT: 0000000000000020 g .text 0000000000000020 .hidden (idx: 11) .hidden_foo[PR]
; XCOFF64-NEXT: 0000000000000040 g .text 0000000000000059 (idx: 13) .bar[PR]
; XCOFF64-NEXT: 00000000000000c0 l .text 000000000000002a (idx: 15) .static_overalign_foo[PR]
; XCOFF64-NEXT: 0000000000000020 g F .text 0000000000000020 .hidden (idx: 11) .hidden_foo[PR]
; XCOFF64-NEXT: 0000000000000040 g F .text 0000000000000059 (idx: 13) .bar[PR]
; XCOFF64-NEXT: 00000000000000c0 l F .text 000000000000002a (idx: 15) .static_overalign_foo[PR]
; XCOFF64-NEXT: 00000000000000f0 g O .data 0000000000000018 (idx: 17) foo[DS]
; XCOFF64-NEXT: 00000000000000f0 g O .data (csect: (idx: 17) foo[DS]) 0000000000000000 (idx: 19) alias_foo
; XCOFF64-NEXT: 0000000000000108 g O .data 0000000000000018 .hidden (idx: 21) hidden_foo[DS]

View File

@ -0,0 +1,33 @@
## Check that llvm-objdump --syms reports an error when
## the symbol type in the csect aux entry of a symbol is not valid.
## Check XCOFF32
# RUN: yaml2obj -DMAGICNUMBER=0x1DF %s -o %t1
# RUN: not llvm-objdump --syms %t1 2>&1 | FileCheck %s -DOBJ=%t1
## Check XCOFF64
# RUN: yaml2obj -DMAGICNUMBER=0x1F7 %s -o %t2
# RUN: not llvm-objdump --syms %t2 2>&1 | FileCheck %s -DOBJ=%t2
# CHECK: error: '[[OBJ]]': symbol csect aux entry with index 2 has invalid symbol type 5
--- !XCOFF
FileHeader:
MagicNumber: [[MAGICNUMBER]]
Sections:
- Name: .text
Flags: [ STYP_TEXT ]
Symbols:
- Name: .file
Section: N_DEBUG
NumberOfAuxEntries: 0
Type: 0x0
StorageClass: C_FILE
- Name: test
Section: .text
NumberOfAuxEntries: 1
StorageClass: C_EXT
AuxEntries:
- Type: AUX_CSECT
SymbolAlignmentAndType: 5
StorageMappingClass: XMC_PR

View File

@ -16,10 +16,10 @@ entry:
ret void
}
; CHECK: ??
; CHECK: .foo
; CHECK: ??:0:0
; CHECK-EMPTY:
; CHECK: ??
; CHECK: .foo1
; CHECK: ??:0:0
; CHECK-EMPTY: