@@ -112,12 +112,13 @@ class InMemoryCASDWARFObject : public DWARFObject {
112
112
// / unit.
113
113
Error partitionCUData (ArrayRef<char > DebugInfoData, uint64_t AbbrevOffset,
114
114
DWARFContext *Ctx, MCCASBuilder &Builder,
115
- AbbrevSetWriter &AbbrevWriter);
115
+ AbbrevSetWriter &AbbrevWriter, uint16_t DwarfVersion );
116
116
};
117
117
118
118
struct CUInfo {
119
119
uint64_t CUSize;
120
120
uint32_t AbbrevOffset;
121
+ uint16_t DwarfVersion;
121
122
};
122
123
static Expected<CUInfo> getAndSetDebugAbbrevOffsetAndSkip (
123
124
MutableArrayRef<char > CUData, support::endianness Endian,
@@ -1685,10 +1686,25 @@ getAndSetDebugAbbrevOffsetAndSkip(MutableArrayRef<char> CUData,
1685
1686
if (auto E = Reader.readInteger (DwarfVersion))
1686
1687
return std::move (E);
1687
1688
1688
- // TODO: Dwarf 5 has a different order for the next fields.
1689
- if (DwarfVersion != 4 )
1690
- return createStringError (inconvertibleErrorCode (),
1691
- " Expected Dwarf 4 input" );
1689
+ if (DwarfVersion >= 5 ) {
1690
+ // From Dwarf 5 Section 7.5.1.1:
1691
+ // Compile Unit Header Format is now changed with unit_type and address_size
1692
+ // after the version. Parse both values from the header.
1693
+ uint8_t UnitType;
1694
+ if (auto E = Reader.readInteger (UnitType))
1695
+ return std::move (E);
1696
+ if (UnitType != dwarf::DW_UT_compile)
1697
+ return createStringError (
1698
+ inconvertibleErrorCode (),
1699
+ " Unit type is not DW_UT_compile, and is incompatible with MCCAS!" );
1700
+ uint8_t AddressSize;
1701
+ if (auto E = Reader.readInteger (AddressSize))
1702
+ return std::move (E);
1703
+ if (AddressSize != 8 )
1704
+ return createStringError (
1705
+ inconvertibleErrorCode (),
1706
+ " Address size is not 8 bytes, unsupported architecture for MCCAS!" );
1707
+ }
1692
1708
1693
1709
// TODO: Handle Dwarf 64 format, which uses 8 bytes.
1694
1710
size_t AbbrevPosition = Reader.getOffset ();
@@ -1710,7 +1726,7 @@ getAndSetDebugAbbrevOffsetAndSkip(MutableArrayRef<char> CUData,
1710
1726
if (auto E = Reader.skip (*Size))
1711
1727
return std::move (E);
1712
1728
1713
- return CUInfo{Reader.getOffset (), AbbrevOffset};
1729
+ return CUInfo{Reader.getOffset (), AbbrevOffset, DwarfVersion };
1714
1730
}
1715
1731
1716
1732
// / Given a list of MCFragments, return a vector with the concatenation of their
@@ -1750,6 +1766,7 @@ MCCASBuilder::splitDebugInfoSectionData(MutableArrayRef<char> DebugInfoData) {
1750
1766
return Info.takeError ();
1751
1767
Split.SplitCUData .push_back (DebugInfoData.take_front (Info->CUSize ));
1752
1768
Split.AbbrevOffsets .push_back (Info->AbbrevOffset );
1769
+ Split.DwarfVersions .push_back (Info->DwarfVersion );
1753
1770
DebugInfoData = DebugInfoData.drop_front (Info->CUSize );
1754
1771
}
1755
1772
@@ -1875,7 +1892,8 @@ Error InMemoryCASDWARFObject::partitionCUData(ArrayRef<char> DebugInfoData,
1875
1892
uint64_t AbbrevOffset,
1876
1893
DWARFContext *Ctx,
1877
1894
MCCASBuilder &Builder,
1878
- AbbrevSetWriter &AbbrevWriter) {
1895
+ AbbrevSetWriter &AbbrevWriter,
1896
+ uint16_t DwarfVersion) {
1879
1897
StringRef AbbrevSectionContribution =
1880
1898
getAbbrevSection ().drop_front (AbbrevOffset);
1881
1899
DataExtractor Data (AbbrevSectionContribution, isLittleEndian (), 8 );
@@ -1894,13 +1912,24 @@ Error InMemoryCASDWARFObject::partitionCUData(ArrayRef<char> DebugInfoData,
1894
1912
1895
1913
DWARFDie CUDie = DCU.getUnitDIE (false );
1896
1914
assert (CUDie);
1897
- // Copy 11 bytes which represents the 32-bit DWARF Header for DWARF4.
1898
- if (DebugInfoData.size () < Dwarf4HeaderSize32Bit)
1899
- return createStringError (inconvertibleErrorCode (),
1900
- " DebugInfoData is too small, it doesn't even "
1901
- " contain a 32-bit DWARF Header" );
1915
+ ArrayRef<char > HeaderData;
1916
+ if (DwarfVersion >= 5 ) {
1917
+ // Copy 12 bytes which represents the 32-bit DWARF Header for DWARF5.
1918
+ if (DebugInfoData.size () < Dwarf5HeaderSize32Bit)
1919
+ return createStringError (inconvertibleErrorCode (),
1920
+ " DebugInfoData is too small, it doesn't even "
1921
+ " contain a 32-bit DWARF5 Header" );
1902
1922
1903
- ArrayRef<char > HeaderData = DebugInfoData.take_front (Dwarf4HeaderSize32Bit);
1923
+ HeaderData = DebugInfoData.take_front (Dwarf5HeaderSize32Bit);
1924
+ } else {
1925
+ // Copy 11 bytes which represents the 32-bit DWARF Header for DWARF4.
1926
+ if (DebugInfoData.size () < Dwarf4HeaderSize32Bit)
1927
+ return createStringError (inconvertibleErrorCode (),
1928
+ " DebugInfoData is too small, it doesn't even "
1929
+ " contain a 32-bit DWARF4 Header" );
1930
+
1931
+ HeaderData = DebugInfoData.take_front (Dwarf4HeaderSize32Bit);
1932
+ }
1904
1933
Expected<DIETopLevelRef> Converted =
1905
1934
DIEToCASConverter (DebugInfoData, Builder)
1906
1935
.convert (CUDie, HeaderData, AbbrevWriter);
@@ -1930,20 +1959,32 @@ Error MCCASBuilder::splitDebugInfoAndAbbrevSections() {
1930
1959
1931
1960
Expected<SmallVector<char , 0 >> FullAbbrevData =
1932
1961
mergeMCFragmentContents (AbbrevFragmentList);
1962
+
1933
1963
if (!FullAbbrevData)
1934
1964
return FullAbbrevData.takeError ();
1935
1965
1936
- InMemoryCASDWARFObject CASObj (
1937
- *FullAbbrevData, Asm.getBackend ().Endian == support::endianness::little);
1966
+ const MCSection::FragmentListType &StringOffsetsFragmentList =
1967
+ DwarfSections.StrOffsets ->getFragmentList ();
1968
+
1969
+ Expected<SmallVector<char , 0 >> FullStringOffsetsData =
1970
+ mergeMCFragmentContents (StringOffsetsFragmentList);
1971
+
1972
+ if (!FullStringOffsetsData)
1973
+ return FullStringOffsetsData.takeError ();
1974
+
1975
+ InMemoryCASDWARFObject CASObj (*FullAbbrevData, *FullStringOffsetsData,
1976
+ Asm.getBackend ().Endian ==
1977
+ support::endianness::little);
1938
1978
auto DWARFObj = std::make_unique<InMemoryCASDWARFObject>(CASObj);
1939
1979
auto DWARFContextHolder = std::make_unique<DWARFContext>(std::move (DWARFObj));
1940
1980
auto *DWARFCtx = DWARFContextHolder.get ();
1941
1981
1942
1982
AbbrevSetWriter AbbrevWriter;
1943
- for (auto [CUData, AbbrevOffset] :
1944
- llvm::zip (SplitInfo->SplitCUData , SplitInfo->AbbrevOffsets )) {
1983
+ for (auto [CUData, AbbrevOffset, DwarfVersion] :
1984
+ llvm::zip (SplitInfo->SplitCUData , SplitInfo->AbbrevOffsets ,
1985
+ SplitInfo->DwarfVersions )) {
1945
1986
if (auto E = CASObj.partitionCUData (CUData, AbbrevOffset, DWARFCtx, *this ,
1946
- AbbrevWriter))
1987
+ AbbrevWriter, DwarfVersion ))
1947
1988
return E;
1948
1989
}
1949
1990
return Error::success ();
@@ -3074,7 +3115,22 @@ Error mccasformats::v1::visitDebugInfo(
3074
3115
StringRef DistinctData = LoadedTopRef->DistinctData .getData ();
3075
3116
BinaryStreamReader DistinctReader (DistinctData, support::endianness::little);
3076
3117
ArrayRef<char > HeaderData;
3077
- if (auto E = DistinctReader.readArray (HeaderData, Dwarf4HeaderSize32Bit))
3118
+
3119
+ auto BeginOffset = DistinctReader.getOffset ();
3120
+ auto Size = getSizeFromDwarfHeader (DistinctReader);
3121
+ if (!Size)
3122
+ return Size.takeError ();
3123
+
3124
+ // 2-byte Dwarf version identifier.
3125
+ uint16_t DwarfVersion;
3126
+ if (auto E = DistinctReader.readInteger (DwarfVersion))
3127
+ return E;
3128
+
3129
+ DistinctReader.setOffset (BeginOffset);
3130
+
3131
+ if (auto E = DistinctReader.readArray (
3132
+ HeaderData,
3133
+ DwarfVersion >= 5 ? Dwarf5HeaderSize32Bit : Dwarf4HeaderSize32Bit))
3078
3134
return E;
3079
3135
HeaderCallback (toStringRef (HeaderData));
3080
3136
0 commit comments