/rust/registry/src/index.crates.io-6f17d22bba15001f/gimli-0.29.0/src/read/pubtypes.rs
Line | Count | Source (jump to first uncovered line) |
1 | | use crate::common::{DebugInfoOffset, SectionId}; |
2 | | use crate::endianity::Endianity; |
3 | | use crate::read::lookup::{DebugLookup, LookupEntryIter, PubStuffEntry, PubStuffParser}; |
4 | | use crate::read::{EndianSlice, Reader, Result, Section, UnitOffset}; |
5 | | |
6 | | /// A single parsed pubtype. |
7 | | #[derive(Debug, Clone)] |
8 | | pub struct PubTypesEntry<R: Reader> { |
9 | | unit_header_offset: DebugInfoOffset<R::Offset>, |
10 | | die_offset: UnitOffset<R::Offset>, |
11 | | name: R, |
12 | | } |
13 | | |
14 | | impl<R: Reader> PubTypesEntry<R> { |
15 | | /// Returns the name of the type this entry refers to. |
16 | 0 | pub fn name(&self) -> &R { |
17 | 0 | &self.name |
18 | 0 | } |
19 | | |
20 | | /// Returns the offset into the .debug_info section for the header of the compilation unit |
21 | | /// which contains the type with this name. |
22 | 0 | pub fn unit_header_offset(&self) -> DebugInfoOffset<R::Offset> { |
23 | 0 | self.unit_header_offset |
24 | 0 | } |
25 | | |
26 | | /// Returns the offset into the compilation unit for the debugging information entry which |
27 | | /// the type with this name. |
28 | 0 | pub fn die_offset(&self) -> UnitOffset<R::Offset> { |
29 | 0 | self.die_offset |
30 | 0 | } |
31 | | } |
32 | | |
33 | | impl<R: Reader> PubStuffEntry<R> for PubTypesEntry<R> { |
34 | 0 | fn new( |
35 | 0 | die_offset: UnitOffset<R::Offset>, |
36 | 0 | name: R, |
37 | 0 | unit_header_offset: DebugInfoOffset<R::Offset>, |
38 | 0 | ) -> Self { |
39 | 0 | PubTypesEntry { |
40 | 0 | unit_header_offset, |
41 | 0 | die_offset, |
42 | 0 | name, |
43 | 0 | } |
44 | 0 | } |
45 | | } |
46 | | |
47 | | /// The `DebugPubTypes` struct represents the DWARF public types information |
48 | | /// found in the `.debug_info` section. |
49 | | #[derive(Debug, Clone)] |
50 | | pub struct DebugPubTypes<R: Reader>(DebugLookup<R, PubStuffParser<R, PubTypesEntry<R>>>); |
51 | | |
52 | | impl<'input, Endian> DebugPubTypes<EndianSlice<'input, Endian>> |
53 | | where |
54 | | Endian: Endianity, |
55 | | { |
56 | | /// Construct a new `DebugPubTypes` instance from the data in the `.debug_pubtypes` |
57 | | /// section. |
58 | | /// |
59 | | /// It is the caller's responsibility to read the `.debug_pubtypes` section and |
60 | | /// present it as a `&[u8]` slice. That means using some ELF loader on |
61 | | /// Linux, a Mach-O loader on macOS, etc. |
62 | | /// |
63 | | /// ``` |
64 | | /// use gimli::{DebugPubTypes, LittleEndian}; |
65 | | /// |
66 | | /// # let buf = []; |
67 | | /// # let read_debug_pubtypes_somehow = || &buf; |
68 | | /// let debug_pubtypes = |
69 | | /// DebugPubTypes::new(read_debug_pubtypes_somehow(), LittleEndian); |
70 | | /// ``` |
71 | 0 | pub fn new(debug_pubtypes_section: &'input [u8], endian: Endian) -> Self { |
72 | 0 | Self::from(EndianSlice::new(debug_pubtypes_section, endian)) |
73 | 0 | } |
74 | | } |
75 | | |
76 | | impl<R: Reader> DebugPubTypes<R> { |
77 | | /// Iterate the pubtypes in the `.debug_pubtypes` section. |
78 | | /// |
79 | | /// ``` |
80 | | /// use gimli::{DebugPubTypes, EndianSlice, LittleEndian}; |
81 | | /// |
82 | | /// # let buf = []; |
83 | | /// # let read_debug_pubtypes_section_somehow = || &buf; |
84 | | /// let debug_pubtypes = |
85 | | /// DebugPubTypes::new(read_debug_pubtypes_section_somehow(), LittleEndian); |
86 | | /// |
87 | | /// let mut iter = debug_pubtypes.items(); |
88 | | /// while let Some(pubtype) = iter.next().unwrap() { |
89 | | /// println!("pubtype {} found!", pubtype.name().to_string_lossy()); |
90 | | /// } |
91 | | /// ``` |
92 | 0 | pub fn items(&self) -> PubTypesEntryIter<R> { |
93 | 0 | PubTypesEntryIter(self.0.items()) |
94 | 0 | } |
95 | | } |
96 | | |
97 | | impl<R: Reader> Section<R> for DebugPubTypes<R> { |
98 | 0 | fn id() -> SectionId { |
99 | 0 | SectionId::DebugPubTypes |
100 | 0 | } |
101 | | |
102 | 0 | fn reader(&self) -> &R { |
103 | 0 | self.0.reader() |
104 | 0 | } |
105 | | } |
106 | | |
107 | | impl<R: Reader> From<R> for DebugPubTypes<R> { |
108 | 0 | fn from(debug_pubtypes_section: R) -> Self { |
109 | 0 | DebugPubTypes(DebugLookup::from(debug_pubtypes_section)) |
110 | 0 | } |
111 | | } |
112 | | |
113 | | /// An iterator over the pubtypes from a `.debug_pubtypes` section. |
114 | | /// |
115 | | /// Can be [used with |
116 | | /// `FallibleIterator`](./index.html#using-with-fallibleiterator). |
117 | | #[derive(Debug, Clone)] |
118 | | pub struct PubTypesEntryIter<R: Reader>(LookupEntryIter<R, PubStuffParser<R, PubTypesEntry<R>>>); |
119 | | |
120 | | impl<R: Reader> PubTypesEntryIter<R> { |
121 | | /// Advance the iterator and return the next pubtype. |
122 | | /// |
123 | | /// Returns the newly parsed pubtype as `Ok(Some(pubtype))`. Returns |
124 | | /// `Ok(None)` when iteration is complete and all pubtypes have already been |
125 | | /// parsed and yielded. If an error occurs while parsing the next pubtype, |
126 | | /// then this error is returned as `Err(e)`, and all subsequent calls return |
127 | | /// `Ok(None)`. |
128 | 0 | pub fn next(&mut self) -> Result<Option<PubTypesEntry<R>>> { |
129 | 0 | self.0.next() |
130 | 0 | } |
131 | | } |
132 | | |
133 | | #[cfg(feature = "fallible-iterator")] |
134 | | impl<R: Reader> fallible_iterator::FallibleIterator for PubTypesEntryIter<R> { |
135 | | type Item = PubTypesEntry<R>; |
136 | | type Error = crate::read::Error; |
137 | | |
138 | | fn next(&mut self) -> ::core::result::Result<Option<Self::Item>, Self::Error> { |
139 | | self.0.next() |
140 | | } |
141 | | } |