1use std::error::Error as StdError;
2use std::fmt;
3
4pub(crate) type Result<T> = std::result::Result<T, Error>;
5
6pub trait AsDynError<'a> {
8 fn as_dyn_error(&self) -> &(dyn StdError + 'a);
9}
10
11impl<'a, T: StdError + 'a> AsDynError<'a> for T {
12 #[inline]
13 fn as_dyn_error(&self) -> &(dyn StdError + 'a) {
14 self
15 }
16}
17
18#[derive(Debug)]
20#[non_exhaustive]
21pub enum Error {
22 ReadInput(std::io::Error),
26 ParseFileKind(object::Error),
31 ParseObjectFile(object::Error),
33 ParseArchiveFile(object::Error),
35 ParseArchiveMember(object::Error),
37 InvalidInputKind,
41 DecompressData(object::Error),
46 NamelessSection(object::Error, usize),
48 RelocationWithInvalidSymbol(String, usize),
50 MultipleRelocations(String, usize),
52 UnsupportedRelocation(String, usize),
54 MissingDwoName(u64),
57 NoCompilationUnits,
59 NoDie,
61 TopLevelDieNotUnit,
63 MissingRequiredSection(&'static str),
65 ParseUnitAbbreviations(gimli::read::Error),
67 ParseUnitHeader(gimli::read::Error),
69 ParseUnit(gimli::read::Error),
71 IncompatibleIndexVersion(String, u16, u16),
73 OffsetAtIndex(gimli::read::Error, u64),
75 StrAtOffset(gimli::read::Error, usize),
77 ParseIndex(gimli::read::Error, String),
82 UnitNotInIndex(u64),
84 RowNotInIndex(gimli::read::Error, u32),
86 SectionNotInRow,
89 ContributionOutOfBounds(crate::index::Contribution, usize),
90 EmptyUnit(u64),
92 MultipleDebugInfoSection,
94 MultipleDebugTypesSection,
96 NotSplitUnit,
98 DuplicateUnit(u64),
100 MissingReferencedUnit(u64),
102 NoOutputObjectCreated,
104 MixedInputEncodings,
106 UnsupportedLocListsEntry(u8),
108 MalformedDebugInfo,
110 UnsupportedForm(u16),
112 UnexpectedSectionAbsoluteReference,
114 GcNotInitialized,
116 GcSharedDwarf4Ranges(crate::package::DwoId),
123
124 Io(std::io::Error),
126 ObjectRead(object::Error),
128 ObjectWrite(object::write::Error),
130 GimliRead(gimli::read::Error),
132 GimliWrite(gimli::write::Error),
134}
135
136impl StdError for Error {
137 fn source(&self) -> Option<&(dyn StdError + 'static)> {
138 match self {
139 Error::ReadInput(source) => Some(source.as_dyn_error()),
140 Error::ParseFileKind(source) => Some(source.as_dyn_error()),
141 Error::ParseObjectFile(source) => Some(source.as_dyn_error()),
142 Error::ParseArchiveFile(source) => Some(source.as_dyn_error()),
143 Error::ParseArchiveMember(source) => Some(source.as_dyn_error()),
144 Error::InvalidInputKind => None,
145 Error::DecompressData(source) => Some(source.as_dyn_error()),
146 Error::NamelessSection(source, _) => Some(source.as_dyn_error()),
147 Error::RelocationWithInvalidSymbol(_, _) => None,
148 Error::MultipleRelocations(_, _) => None,
149 Error::UnsupportedRelocation(_, _) => None,
150 Error::MissingDwoName(_) => None,
151 Error::NoCompilationUnits => None,
152 Error::NoDie => None,
153 Error::TopLevelDieNotUnit => None,
154 Error::MissingRequiredSection(_) => None,
155 Error::ParseUnitAbbreviations(source) => Some(source.as_dyn_error()),
156 Error::ParseUnitHeader(source) => Some(source.as_dyn_error()),
157 Error::ParseUnit(source) => Some(source.as_dyn_error()),
158 Error::IncompatibleIndexVersion(_, _, _) => None,
159 Error::OffsetAtIndex(source, _) => Some(source.as_dyn_error()),
160 Error::StrAtOffset(source, _) => Some(source.as_dyn_error()),
161 Error::ParseIndex(source, _) => Some(source.as_dyn_error()),
162 Error::UnitNotInIndex(_) => None,
163 Error::RowNotInIndex(source, _) => Some(source.as_dyn_error()),
164 Error::SectionNotInRow => None,
165 Error::ContributionOutOfBounds(..) => None,
166 Error::EmptyUnit(_) => None,
167 Error::MultipleDebugInfoSection => None,
168 Error::MultipleDebugTypesSection => None,
169 Error::NotSplitUnit => None,
170 Error::DuplicateUnit(_) => None,
171 Error::MissingReferencedUnit(_) => None,
172 Error::NoOutputObjectCreated => None,
173 Error::MixedInputEncodings => None,
174 Error::UnsupportedLocListsEntry(_) => None,
175 Error::MalformedDebugInfo => None,
176 Error::UnsupportedForm(_) => None,
177 Error::UnexpectedSectionAbsoluteReference => None,
178 Error::GcNotInitialized => None,
179 Error::GcSharedDwarf4Ranges(_) => None,
180 Error::Io(transparent) => StdError::source(transparent.as_dyn_error()),
181 Error::ObjectRead(transparent) => StdError::source(transparent.as_dyn_error()),
182 Error::ObjectWrite(transparent) => StdError::source(transparent.as_dyn_error()),
183 Error::GimliRead(transparent) => StdError::source(transparent.as_dyn_error()),
184 Error::GimliWrite(transparent) => StdError::source(transparent.as_dyn_error()),
185 }
186 }
187}
188
189impl fmt::Display for Error {
190 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
191 match self {
192 Error::ReadInput(_) => write!(f, "Failed to read input file"),
193 Error::ParseFileKind(_) => write!(f, "Failed to parse input file kind"),
194 Error::ParseObjectFile(_) => write!(f, "Failed to parse input object file"),
195 Error::ParseArchiveFile(_) => write!(f, "Failed to parse input archive file"),
196 Error::ParseArchiveMember(_) => write!(f, "Failed to parse archive member"),
197 Error::InvalidInputKind => write!(f, "Input is not an archive or elf object"),
198 Error::DecompressData(_) => write!(f, "Failed to decompress compressed section"),
199 Error::NamelessSection(_, offset) => {
200 write!(f, "Section without name at offset 0x{:08x}", offset)
201 }
202 Error::RelocationWithInvalidSymbol(section, offset) => write!(
203 f,
204 "Relocation with invalid symbol for section `{}` at offset 0x{:08x}",
205 section, offset
206 ),
207 Error::MultipleRelocations(section, offset) => write!(
208 f,
209 "Multiple relocations for section `{}` at offset 0x{:08x}",
210 section, offset
211 ),
212 Error::UnsupportedRelocation(section, offset) => write!(
213 f,
214 "Unsupported relocation for section {} at offset 0x{:08x}",
215 section, offset
216 ),
217 Error::MissingDwoName(id) => {
218 write!(f, "Missing path attribute to DWARF object (0x{:08x})", id)
219 }
220 Error::NoCompilationUnits => {
221 write!(f, "Input object has no compilation units")
222 }
223 Error::NoDie => {
224 write!(f, "No top-level debugging information entry in compilation/type unit")
225 }
226 Error::TopLevelDieNotUnit => {
227 write!(f, "Top-level debugging information entry is not a compilation/type unit")
228 }
229 Error::MissingRequiredSection(section) => {
230 write!(f, "Input object missing required section `{}`", section)
231 }
232 Error::ParseUnitAbbreviations(_) => write!(f, "Failed to parse unit abbreviations"),
233 Error::ParseUnitHeader(_) => write!(f, "Failed to parse unit header"),
234 Error::ParseUnit(_) => write!(f, "Failed to parse unit"),
235 Error::IncompatibleIndexVersion(section, format, actual) => {
236 write!(
237 f,
238 "Incompatible `{}` index version: found version {}, expected version {}",
239 section, actual, format
240 )
241 }
242 Error::OffsetAtIndex(_, index) => {
243 write!(f, "Read offset at index {} of `.debug_str_offsets.dwo` section", index)
244 }
245 Error::StrAtOffset(_, offset) => {
246 write!(f, "Read string at offset 0x{:08x} of `.debug_str.dwo` section", offset)
247 }
248 Error::ParseIndex(_, section) => {
249 write!(f, "Failed to parse `{}` index section", section)
250 }
251 Error::UnitNotInIndex(unit) => {
252 write!(f, "Unit 0x{0:08x} from input package is not in its index", unit)
253 }
254 Error::RowNotInIndex(_, row) => {
255 write!(f, "Row {0} found in index's hash table not present in index", row)
256 }
257 Error::SectionNotInRow => write!(f, "Section not found in unit's row in index"),
258 Error::ContributionOutOfBounds(contribution, section_len) => {
259 write!(
260 f,
261 "Index contribution at offset 0x{:08x} with size 0x{:x} extends beyond section \
262 of length 0x{:x}",
263 contribution.offset.0, contribution.size, section_len
264 )
265 }
266 Error::EmptyUnit(unit) => {
267 write!(f, "Unit 0x{:08x} in input DWARF object with no data", unit)
268 }
269 Error::MultipleDebugInfoSection => {
270 write!(f, "Multiple `.debug_info.dwo` sections")
271 }
272 Error::MultipleDebugTypesSection => {
273 write!(f, "Multiple `.debug_types.dwo` sections in a package")
274 }
275 Error::NotSplitUnit => {
276 write!(f, "Regular compilation unit in object (missing dwo identifier)")
277 }
278 Error::DuplicateUnit(unit) => {
279 write!(f, "Duplicate split compilation unit (0x{:08x})", unit)
280 }
281 Error::MissingReferencedUnit(unit) => {
282 write!(f, "Unit 0x{:08x} referenced by executable was not found", unit)
283 }
284 Error::NoOutputObjectCreated => write!(f, "No output object was created from inputs"),
285 Error::MixedInputEncodings => write!(f, "Input objects haved mixed encodings"),
286 Error::UnsupportedLocListsEntry(s) => {
287 write!(f, "Unsupported DW_LLE value: {}", s)
288 }
289 Error::MalformedDebugInfo => write!(f, "Malformed `.debug_info.dwo` compilation unit"),
290 Error::UnsupportedForm(form) => {
291 write!(f, "Unsupported DWARF form 0x{:02x} during GC rewrite", form)
292 }
293 Error::UnexpectedSectionAbsoluteReference => {
294 write!(f, "A section-absolute reference was found in a .dwo file")
295 }
296 Error::GcNotInitialized => {
297 write!(f, "GC was requested but no executables were preprocessed")
298 }
299 Error::GcSharedDwarf4Ranges(dwo_id) => {
300 write!(
301 f,
302 "DWARF4 .debug_ranges for {dwo_id:?} is supplied by multiple executables; \
303 cannot safely GC"
304 )
305 }
306 Error::Io(e) => fmt::Display::fmt(e, f),
307 Error::ObjectRead(e) => fmt::Display::fmt(e, f),
308 Error::ObjectWrite(e) => fmt::Display::fmt(e, f),
309 Error::GimliRead(e) => fmt::Display::fmt(e, f),
310 Error::GimliWrite(e) => fmt::Display::fmt(e, f),
311 }
312 }
313}
314
315impl From<std::io::Error> for Error {
316 fn from(source: std::io::Error) -> Self {
317 Error::Io(source)
318 }
319}
320
321impl From<object::Error> for Error {
322 fn from(source: object::Error) -> Self {
323 Error::ObjectRead(source)
324 }
325}
326
327impl From<object::write::Error> for Error {
328 fn from(source: object::write::Error) -> Self {
329 Error::ObjectWrite(source)
330 }
331}
332
333impl From<gimli::read::Error> for Error {
334 fn from(source: gimli::read::Error) -> Self {
335 Error::GimliRead(source)
336 }
337}
338
339impl From<gimli::write::Error> for Error {
340 fn from(source: gimli::write::Error) -> Self {
341 Error::GimliWrite(source)
342 }
343}