Skip to content

[XCOFF][obj2yaml] Support SymbolAlignmentAndType as 2 separate fields in YAML. #76828

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Feb 8, 2024
7 changes: 7 additions & 0 deletions llvm/include/llvm/ObjectYAML/XCOFFYAML.h
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,9 @@ struct CsectAuxEnt : AuxSymbolEnt {
// Common fields for both XCOFF32 and XCOFF64.
std::optional<uint32_t> ParameterHashIndex;
std::optional<uint16_t> TypeChkSectNum;
std::optional<XCOFF::SymbolType> SymbolType;
std::optional<uint8_t> SymbolAlignment;
// The two previous values can be encoded as a single value.
std::optional<uint8_t> SymbolAlignmentAndType;
std::optional<XCOFF::StorageMappingClass> StorageMappingClass;

Expand Down Expand Up @@ -237,6 +240,10 @@ template <> struct ScalarEnumerationTraits<XCOFF::StorageMappingClass> {
static void enumeration(IO &IO, XCOFF::StorageMappingClass &Value);
};

template <> struct ScalarEnumerationTraits<XCOFF::SymbolType> {
static void enumeration(IO &IO, XCOFF::SymbolType &Value);
};

template <> struct ScalarEnumerationTraits<XCOFF::CFileStringType> {
static void enumeration(IO &IO, XCOFF::CFileStringType &Type);
};
Expand Down
99 changes: 70 additions & 29 deletions llvm/lib/ObjectYAML/XCOFFEmitter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
#include "llvm/Support/raw_ostream.h"

using namespace llvm;
using namespace llvm::object;

namespace {

Expand Down Expand Up @@ -56,14 +57,14 @@ class XCOFFWriter {
bool writeSymbols();
void writeStringTable();

void writeAuxSymbol(const XCOFFYAML::CsectAuxEnt &AuxSym);
void writeAuxSymbol(const XCOFFYAML::FileAuxEnt &AuxSym);
void writeAuxSymbol(const XCOFFYAML::FunctionAuxEnt &AuxSym);
void writeAuxSymbol(const XCOFFYAML::ExcpetionAuxEnt &AuxSym);
void writeAuxSymbol(const XCOFFYAML::BlockAuxEnt &AuxSym);
void writeAuxSymbol(const XCOFFYAML::SectAuxEntForDWARF &AuxSym);
void writeAuxSymbol(const XCOFFYAML::SectAuxEntForStat &AuxSym);
void writeAuxSymbol(const std::unique_ptr<XCOFFYAML::AuxSymbolEnt> &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::CsectAuxEnt &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::FileAuxEnt &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::FunctionAuxEnt &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::ExcpetionAuxEnt &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::BlockAuxEnt &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::SectAuxEntForDWARF &AuxSym);
bool writeAuxSymbol(const XCOFFYAML::SectAuxEntForStat &AuxSym);
bool writeAuxSymbol(const std::unique_ptr<XCOFFYAML::AuxSymbolEnt> &AuxSym);

XCOFFYAML::Object &Obj;
bool Is64Bit = false;
Expand Down Expand Up @@ -181,7 +182,7 @@ bool XCOFFWriter::initStringTable() {
StrTblBuilder.clear();

if (Obj.StrTbl.Strings) {
// All specified strings should be added to the string table.
// Add all specified strings to the string table.
for (StringRef StringEnt : *Obj.StrTbl.Strings)
StrTblBuilder.add(StringEnt);

Expand Down Expand Up @@ -524,12 +525,44 @@ bool XCOFFWriter::writeRelocations() {
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::CsectAuxEnt &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::CsectAuxEnt &AuxSym) {
uint8_t SymAlignAndType = 0;
if (AuxSym.SymbolAlignmentAndType) {
if (AuxSym.SymbolType || AuxSym.SymbolAlignment) {
ErrHandler("cannot specify SymbolType or SymbolAlignment if "
"SymbolAlignmentAndType is specified");
return false;
}
SymAlignAndType = *AuxSym.SymbolAlignmentAndType;
} else {
if (AuxSym.SymbolType) {
uint8_t SymbolType = *AuxSym.SymbolType;
if (SymbolType & ~XCOFFCsectAuxRef::SymbolTypeMask) {
ErrHandler("symbol type must be less than " +
Twine(1 + XCOFFCsectAuxRef::SymbolTypeMask));
return false;
}
SymAlignAndType = SymbolType;
}
if (AuxSym.SymbolAlignment) {
const uint8_t ShiftedSymbolAlignmentMask =
XCOFFCsectAuxRef::SymbolAlignmentMask >>
XCOFFCsectAuxRef::SymbolAlignmentBitOffset;

if (*AuxSym.SymbolAlignment & ~ShiftedSymbolAlignmentMask) {
ErrHandler("symbol alignment must be less than " +
Twine(1 + ShiftedSymbolAlignmentMask));
return false;
}
SymAlignAndType |= (*AuxSym.SymbolAlignment
<< XCOFFCsectAuxRef::SymbolAlignmentBitOffset);
}
}
if (Is64Bit) {
W.write<uint32_t>(AuxSym.SectionOrLengthLo.value_or(0));
W.write<uint32_t>(AuxSym.ParameterHashIndex.value_or(0));
W.write<uint16_t>(AuxSym.TypeChkSectNum.value_or(0));
W.write<uint8_t>(AuxSym.SymbolAlignmentAndType.value_or(0));
W.write<uint8_t>(SymAlignAndType);
W.write<uint8_t>(AuxSym.StorageMappingClass.value_or(XCOFF::XMC_PR));
W.write<uint32_t>(AuxSym.SectionOrLengthHi.value_or(0));
W.write<uint8_t>(0);
Expand All @@ -538,23 +571,25 @@ void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::CsectAuxEnt &AuxSym) {
W.write<uint32_t>(AuxSym.SectionOrLength.value_or(0));
W.write<uint32_t>(AuxSym.ParameterHashIndex.value_or(0));
W.write<uint16_t>(AuxSym.TypeChkSectNum.value_or(0));
W.write<uint8_t>(AuxSym.SymbolAlignmentAndType.value_or(0));
W.write<uint8_t>(SymAlignAndType);
W.write<uint8_t>(AuxSym.StorageMappingClass.value_or(XCOFF::XMC_PR));
W.write<uint32_t>(AuxSym.StabInfoIndex.value_or(0));
W.write<uint16_t>(AuxSym.StabSectNum.value_or(0));
}
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::ExcpetionAuxEnt &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::ExcpetionAuxEnt &AuxSym) {
assert(Is64Bit && "can't write the exception auxiliary symbol for XCOFF32");
W.write<uint64_t>(AuxSym.OffsetToExceptionTbl.value_or(0));
W.write<uint32_t>(AuxSym.SizeOfFunction.value_or(0));
W.write<uint32_t>(AuxSym.SymIdxOfNextBeyond.value_or(0));
W.write<uint8_t>(0);
W.write<uint8_t>(XCOFF::AUX_EXCEPT);
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FunctionAuxEnt &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FunctionAuxEnt &AuxSym) {
if (Is64Bit) {
W.write<uint64_t>(AuxSym.PtrToLineNum.value_or(0));
W.write<uint32_t>(AuxSym.SizeOfFunction.value_or(0));
Expand All @@ -568,9 +603,10 @@ void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FunctionAuxEnt &AuxSym) {
W.write<uint32_t>(AuxSym.SymIdxOfNextBeyond.value_or(0));
W.OS.write_zeros(2);
}
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FileAuxEnt &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FileAuxEnt &AuxSym) {
StringRef FileName = AuxSym.FileNameOrString.value_or("");
if (nameShouldBeInStringTable(FileName)) {
W.write<int32_t>(0);
Expand All @@ -586,9 +622,10 @@ void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::FileAuxEnt &AuxSym) {
} else {
W.OS.write_zeros(3);
}
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::BlockAuxEnt &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::BlockAuxEnt &AuxSym) {
if (Is64Bit) {
W.write<uint32_t>(AuxSym.LineNum.value_or(0));
W.OS.write_zeros(13);
Expand All @@ -599,9 +636,10 @@ void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::BlockAuxEnt &AuxSym) {
W.write<uint16_t>(AuxSym.LineNumLo.value_or(0));
W.OS.write_zeros(12);
}
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::SectAuxEntForDWARF &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::SectAuxEntForDWARF &AuxSym) {
if (Is64Bit) {
W.write<uint64_t>(AuxSym.LengthOfSectionPortion.value_or(0));
W.write<uint64_t>(AuxSym.NumberOfRelocEnt.value_or(0));
Expand All @@ -613,34 +651,36 @@ void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::SectAuxEntForDWARF &AuxSym) {
W.write<uint32_t>(AuxSym.NumberOfRelocEnt.value_or(0));
W.OS.write_zeros(6);
}
return true;
}

void XCOFFWriter::writeAuxSymbol(const XCOFFYAML::SectAuxEntForStat &AuxSym) {
bool XCOFFWriter::writeAuxSymbol(const XCOFFYAML::SectAuxEntForStat &AuxSym) {
assert(!Is64Bit && "can't write the stat auxiliary symbol for XCOFF64");
W.write<uint32_t>(AuxSym.SectionLength.value_or(0));
W.write<uint16_t>(AuxSym.NumberOfRelocEnt.value_or(0));
W.write<uint16_t>(AuxSym.NumberOfLineNum.value_or(0));
W.OS.write_zeros(10);
return true;
}

void XCOFFWriter::writeAuxSymbol(
bool XCOFFWriter::writeAuxSymbol(
const std::unique_ptr<XCOFFYAML::AuxSymbolEnt> &AuxSym) {
if (auto AS = dyn_cast<XCOFFYAML::CsectAuxEnt>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::FunctionAuxEnt>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::ExcpetionAuxEnt>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::FileAuxEnt>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::BlockAuxEnt>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::SectAuxEntForDWARF>(AuxSym.get()))
writeAuxSymbol(*AS);
return writeAuxSymbol(*AS);
else if (auto AS = dyn_cast<XCOFFYAML::SectAuxEntForStat>(AuxSym.get()))
writeAuxSymbol(*AS);
else
llvm_unreachable("unknown auxiliary symbol type");
return writeAuxSymbol(*AS);
llvm_unreachable("unknown auxiliary symbol type");
return false;
}

bool XCOFFWriter::writeSymbols() {
Expand Down Expand Up @@ -698,7 +738,8 @@ bool XCOFFWriter::writeSymbols() {
} else {
for (const std::unique_ptr<XCOFFYAML::AuxSymbolEnt> &AuxSym :
YamlSym.AuxEntries) {
writeAuxSymbol(AuxSym);
if (!writeAuxSymbol(AuxSym))
return false;
}
// Pad with zeros.
if (NumOfAuxSym > YamlSym.AuxEntries.size())
Expand Down
16 changes: 15 additions & 1 deletion llvm/lib/ObjectYAML/XCOFFYAML.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,17 @@ void ScalarEnumerationTraits<XCOFF::StorageMappingClass>::enumeration(
#undef ECase
}

void ScalarEnumerationTraits<XCOFF::SymbolType>::enumeration(
IO &IO, XCOFF::SymbolType &Value) {
#define ECase(X) IO.enumCase(Value, #X, XCOFF::X)
ECase(XTY_ER);
ECase(XTY_SD);
ECase(XTY_LD);
ECase(XTY_CM);
#undef ECase
IO.enumFallback<Hex8>(Value);
}

void ScalarEnumerationTraits<XCOFFYAML::AuxSymbolType>::enumeration(
IO &IO, XCOFFYAML::AuxSymbolType &Type) {
#define ECase(X) IO.enumCase(Type, #X, XCOFFYAML::X)
Expand Down Expand Up @@ -229,6 +240,8 @@ static void auxSymMapping(IO &IO, XCOFFYAML::CsectAuxEnt &AuxSym, bool Is64) {
IO.mapOptional("ParameterHashIndex", AuxSym.ParameterHashIndex);
IO.mapOptional("TypeChkSectNum", AuxSym.TypeChkSectNum);
IO.mapOptional("SymbolAlignmentAndType", AuxSym.SymbolAlignmentAndType);
IO.mapOptional("SymbolType", AuxSym.SymbolType);
IO.mapOptional("SymbolAlignment", AuxSym.SymbolAlignment);
IO.mapOptional("StorageMappingClass", AuxSym.StorageMappingClass);
if (Is64) {
IO.mapOptional("SectionOrLengthLo", AuxSym.SectionOrLengthLo);
Expand Down Expand Up @@ -350,7 +363,8 @@ void MappingTraits<XCOFFYAML::Symbol>::mapping(IO &IO, XCOFFYAML::Symbol &S) {
IO.mapOptional("AuxEntries", S.AuxEntries);
}

void MappingTraits<XCOFFYAML::StringTable>::mapping(IO &IO, XCOFFYAML::StringTable &Str) {
void MappingTraits<XCOFFYAML::StringTable>::mapping(
IO &IO, XCOFFYAML::StringTable &Str) {
IO.mapOptional("ContentSize", Str.ContentSize);
IO.mapOptional("Length", Str.Length);
IO.mapOptional("Strings", Str.Strings);
Expand Down
12 changes: 8 additions & 4 deletions llvm/test/tools/obj2yaml/XCOFF/aix.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,8 @@
# CHECK32-NEXT: - Type: AUX_CSECT
# CHECK32-NEXT: ParameterHashIndex: 0
# CHECK32-NEXT: TypeChkSectNum: 0
# CHECK32-NEXT: SymbolAlignmentAndType: 0
# CHECK32-NEXT: SymbolType: XTY_ER
# CHECK32-NEXT: SymbolAlignment: 0
# CHECK32-NEXT: StorageMappingClass: XMC_PR
# CHECK32-NEXT: SectionOrLength: 0
# CHECK32-NEXT: StabInfoIndex: 0
Expand All @@ -71,7 +72,8 @@
# CHECK32-NEXT: - Type: AUX_CSECT
# CHECK32-NEXT: ParameterHashIndex: 0
# CHECK32-NEXT: TypeChkSectNum: 0
# CHECK32-NEXT: SymbolAlignmentAndType: 0
# CHECK32-NEXT: SymbolType: XTY_ER
# CHECK32-NEXT: SymbolAlignment: 0
# CHECK32-NEXT: StorageMappingClass: XMC_PR
# CHECK32-NEXT: SectionOrLength: 0
# CHECK32-NEXT: StabInfoIndex: 0
Expand Down Expand Up @@ -128,7 +130,8 @@
# CHECK64-NEXT: - Type: AUX_CSECT
# CHECK64-NEXT: ParameterHashIndex: 0
# CHECK64-NEXT: TypeChkSectNum: 0
# CHECK64-NEXT: SymbolAlignmentAndType: 0
# CHECK64-NEXT: SymbolType: XTY_ER
# CHECK64-NEXT: SymbolAlignment: 0
# CHECK64-NEXT: StorageMappingClass: XMC_PR
# CHECK64-NEXT: SectionOrLengthLo: 0
# CHECK64-NEXT: SectionOrLengthHi: 0
Expand All @@ -142,7 +145,8 @@
# CHECK64-NEXT: - Type: AUX_CSECT
# CHECK64-NEXT: ParameterHashIndex: 0
# CHECK64-NEXT: TypeChkSectNum: 0
# CHECK64-NEXT: SymbolAlignmentAndType: 0
# CHECK64-NEXT: SymbolType: XTY_ER
# CHECK64-NEXT: SymbolAlignment: 0
# CHECK64-NEXT: StorageMappingClass: XMC_PR
# CHECK64-NEXT: SectionOrLengthLo: 0
# CHECK64-NEXT: SectionOrLengthHi: 0
Expand Down
12 changes: 8 additions & 4 deletions llvm/test/tools/obj2yaml/XCOFF/aux-symbols.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@
# CHECK32-NEXT: - Type: AUX_CSECT
# CHECK32-NEXT: ParameterHashIndex: 1
# CHECK32-NEXT: TypeChkSectNum: 2
# CHECK32-NEXT: SymbolAlignmentAndType: 41
# CHECK32-NEXT: SymbolType: XTY_SD
# CHECK32-NEXT: SymbolAlignment: 5
# CHECK32-NEXT: StorageMappingClass: XMC_PR
# CHECK32-NEXT: SectionOrLength: 3
# CHECK32-NEXT: StabInfoIndex: 4
Expand All @@ -54,7 +55,8 @@
# CHECK32-NEXT: - Type: AUX_CSECT
# CHECK32-NEXT: ParameterHashIndex: 1
# CHECK32-NEXT: TypeChkSectNum: 2
# CHECK32-NEXT: SymbolAlignmentAndType: 17
# CHECK32-NEXT: SymbolType: XTY_SD
# CHECK32-NEXT: SymbolAlignment: 2
# CHECK32-NEXT: StorageMappingClass: XMC_PR
# CHECK32-NEXT: SectionOrLength: 4
# CHECK32-NEXT: StabInfoIndex: 5
Expand Down Expand Up @@ -174,7 +176,8 @@ Symbols:
# CHECK64-NEXT: - Type: AUX_CSECT
# CHECK64-NEXT: ParameterHashIndex: 1
# CHECK64-NEXT: TypeChkSectNum: 2
# CHECK64-NEXT: SymbolAlignmentAndType: 41
# CHECK64-NEXT: SymbolType: XTY_SD
# CHECK64-NEXT: SymbolAlignment: 5
# CHECK64-NEXT: StorageMappingClass: XMC_PR
# CHECK64-NEXT: SectionOrLengthLo: 3
# CHECK64-NEXT: SectionOrLengthHi: 4
Expand All @@ -196,7 +199,8 @@ Symbols:
# CHECK64-NEXT: - Type: AUX_CSECT
# CHECK64-NEXT: ParameterHashIndex: 1
# CHECK64-NEXT: TypeChkSectNum: 2
# CHECK64-NEXT: SymbolAlignmentAndType: 17
# CHECK64-NEXT: SymbolType: XTY_SD
# CHECK64-NEXT: SymbolAlignment: 2
# CHECK64-NEXT: StorageMappingClass: XMC_PR
# CHECK64-NEXT: SectionOrLengthLo: 3
# CHECK64-NEXT: SectionOrLengthHi: 4
Expand Down
Loading