1 // Copyright 2022, The Android Open Source Project
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 //! Iterators over cells, and various layers on top of them.
16 
17 use crate::Fdt;
18 use crate::FdtError;
19 use crate::FdtNode;
20 use crate::FdtProperty;
21 use crate::{AddrCells, SizeCells};
22 use core::ffi::CStr;
23 use core::marker::PhantomData;
24 use core::{mem::size_of, ops::Range, slice::ChunksExact};
25 
26 use zerocopy::transmute;
27 
28 /// Iterator over nodes sharing a same compatible string.
29 pub struct CompatibleIterator<'a> {
30     node: FdtNode<'a>,
31     compatible: &'a CStr,
32 }
33 
34 impl<'a> CompatibleIterator<'a> {
new(fdt: &'a Fdt, compatible: &'a CStr) -> Result<Self, FdtError>35     pub(crate) fn new(fdt: &'a Fdt, compatible: &'a CStr) -> Result<Self, FdtError> {
36         let node = fdt.root();
37         Ok(Self { node, compatible })
38     }
39 }
40 
41 impl<'a> Iterator for CompatibleIterator<'a> {
42     type Item = FdtNode<'a>;
43 
next(&mut self) -> Option<Self::Item>44     fn next(&mut self) -> Option<Self::Item> {
45         let next = self.node.next_compatible(self.compatible).ok()?;
46 
47         if let Some(node) = next {
48             self.node = node;
49         }
50 
51         next
52     }
53 }
54 
55 /// Iterator over cells of a DT property.
56 #[derive(Debug)]
57 pub struct CellIterator<'a> {
58     chunks: ChunksExact<'a, u8>,
59 }
60 
61 impl<'a> CellIterator<'a> {
new(bytes: &'a [u8]) -> Self62     pub(crate) fn new(bytes: &'a [u8]) -> Self {
63         const CHUNK_SIZE: usize = size_of::<<CellIterator as Iterator>::Item>();
64 
65         Self { chunks: bytes.chunks_exact(CHUNK_SIZE) }
66     }
67 }
68 
69 impl<'a> Iterator for CellIterator<'a> {
70     type Item = u32;
71 
next(&mut self) -> Option<Self::Item>72     fn next(&mut self) -> Option<Self::Item> {
73         Some(Self::Item::from_be_bytes(self.chunks.next()?.try_into().ok()?))
74     }
75 }
76 
77 /// Iterator over a 'reg' property of a DT node.
78 #[derive(Debug)]
79 pub struct RegIterator<'a> {
80     cells: CellIterator<'a>,
81     addr_cells: AddrCells,
82     size_cells: SizeCells,
83 }
84 
85 /// Represents a contiguous region within the address space defined by the parent bus.
86 /// Commonly means the offsets and lengths of MMIO blocks, but may have a different meaning on some
87 /// bus types. Addresses in the address space defined by the root node are CPU real addresses.
88 #[derive(Copy, Clone, Debug)]
89 pub struct Reg<T> {
90     /// Base address of the region.
91     pub addr: T,
92     /// Size of the region (optional).
93     pub size: Option<T>,
94 }
95 
96 impl<T: TryInto<usize>> TryFrom<Reg<T>> for Range<usize> {
97     type Error = FdtError;
98 
try_from(reg: Reg<T>) -> Result<Self, Self::Error>99     fn try_from(reg: Reg<T>) -> Result<Self, Self::Error> {
100         let addr = to_usize(reg.addr)?;
101         let size = to_usize(reg.size.ok_or(FdtError::NotFound)?)?;
102         let end = addr.checked_add(size).ok_or(FdtError::BadValue)?;
103         Ok(addr..end)
104     }
105 }
106 
to_usize<T: TryInto<usize>>(num: T) -> Result<usize, FdtError>107 fn to_usize<T: TryInto<usize>>(num: T) -> Result<usize, FdtError> {
108     num.try_into().map_err(|_| FdtError::BadValue)
109 }
110 
111 impl<'a> RegIterator<'a> {
new( cells: CellIterator<'a>, addr_cells: AddrCells, size_cells: SizeCells, ) -> Self112     pub(crate) fn new(
113         cells: CellIterator<'a>,
114         addr_cells: AddrCells,
115         size_cells: SizeCells,
116     ) -> Self {
117         Self { cells, addr_cells, size_cells }
118     }
119 }
120 
121 impl<'a> Iterator for RegIterator<'a> {
122     type Item = Reg<u64>;
123 
next(&mut self) -> Option<Self::Item>124     fn next(&mut self) -> Option<Self::Item> {
125         let addr = FromAddrCells::from_addr_cells(&mut self.cells, self.addr_cells)?;
126         // If the parent node specifies a value of 0 for #size-cells, 'size' shall be omitted.
127         let size = if self.size_cells == SizeCells::None {
128             None
129         } else {
130             Some(FromSizeCells::from_size_cells(&mut self.cells, self.size_cells)?)
131         };
132 
133         Some(Self::Item { addr, size })
134     }
135 }
136 
137 impl Reg<u64> {
138     const NUM_CELLS: usize = 2;
139     /// Converts addr and (optional) size to the format that is consumable by libfdt.
to_cells( &self, ) -> ([u8; Self::NUM_CELLS * size_of::<u32>()], Option<[u8; Self::NUM_CELLS * size_of::<u32>()]>)140     pub fn to_cells(
141         &self,
142     ) -> ([u8; Self::NUM_CELLS * size_of::<u32>()], Option<[u8; Self::NUM_CELLS * size_of::<u32>()]>)
143     {
144         let addr = transmute!([((self.addr >> 32) as u32).to_be(), (self.addr as u32).to_be()]);
145         let size =
146             self.size.map(|sz| transmute!([((sz >> 32) as u32).to_be(), (sz as u32).to_be()]));
147 
148         (addr, size)
149     }
150 }
151 
152 /// Iterator over the address ranges defined by the /memory/ node.
153 #[derive(Debug)]
154 pub struct MemRegIterator<'a> {
155     reg: RegIterator<'a>,
156 }
157 
158 impl<'a> MemRegIterator<'a> {
new(reg: RegIterator<'a>) -> Self159     pub(crate) fn new(reg: RegIterator<'a>) -> Self {
160         Self { reg }
161     }
162 }
163 
164 impl<'a> Iterator for MemRegIterator<'a> {
165     type Item = Range<usize>;
166 
next(&mut self) -> Option<Self::Item>167     fn next(&mut self) -> Option<Self::Item> {
168         let next = self.reg.next()?;
169         let addr = usize::try_from(next.addr).ok()?;
170         let size = usize::try_from(next.size?).ok()?;
171 
172         Some(addr..addr.checked_add(size)?)
173     }
174 }
175 
176 /// Iterator over the 'ranges' property of a DT node.
177 #[derive(Debug)]
178 pub struct RangesIterator<'a, A, P, S> {
179     cells: CellIterator<'a>,
180     addr_cells: AddrCells,
181     parent_addr_cells: AddrCells,
182     size_cells: SizeCells,
183     _addr: PhantomData<A>,
184     _parent_addr: PhantomData<P>,
185     _size: PhantomData<S>,
186 }
187 
188 /// An address range from the 'ranges' property of a DT node.
189 #[derive(Clone, Debug, Default)]
190 pub struct AddressRange<A, P, S> {
191     /// The physical address of the range within the child bus's address space.
192     pub addr: A,
193     /// The physical address of the range in the parent bus's address space.
194     pub parent_addr: P,
195     /// The size of the range in the child's address space.
196     pub size: S,
197 }
198 
199 impl<'a, A, P, S> RangesIterator<'a, A, P, S> {
new( cells: CellIterator<'a>, addr_cells: AddrCells, parent_addr_cells: AddrCells, size_cells: SizeCells, ) -> Self200     pub(crate) fn new(
201         cells: CellIterator<'a>,
202         addr_cells: AddrCells,
203         parent_addr_cells: AddrCells,
204         size_cells: SizeCells,
205     ) -> Self {
206         Self {
207             cells,
208             addr_cells,
209             parent_addr_cells,
210             size_cells,
211             _addr: Default::default(),
212             _parent_addr: Default::default(),
213             _size: Default::default(),
214         }
215     }
216 }
217 
218 impl<'a, A: FromAddrCells, P: FromAddrCells, S: FromSizeCells> Iterator
219     for RangesIterator<'a, A, P, S>
220 {
221     type Item = AddressRange<A, P, S>;
222 
next(&mut self) -> Option<Self::Item>223     fn next(&mut self) -> Option<Self::Item> {
224         let addr = FromAddrCells::from_addr_cells(&mut self.cells, self.addr_cells)?;
225         let parent_addr = FromAddrCells::from_addr_cells(&mut self.cells, self.parent_addr_cells)?;
226         let size = FromSizeCells::from_size_cells(&mut self.cells, self.size_cells)?;
227         Some(AddressRange { addr, parent_addr, size })
228     }
229 }
230 
231 trait FromAddrCells: Sized {
from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self>232     fn from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self>;
233 }
234 
235 impl FromAddrCells for u64 {
from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self>236     fn from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self> {
237         Some(match cell_count {
238             AddrCells::Single => cells.next()?.into(),
239             AddrCells::Double => (cells.next()? as Self) << 32 | cells.next()? as Self,
240             _ => panic!("Invalid addr_cells {:?} for u64", cell_count),
241         })
242     }
243 }
244 
245 impl FromAddrCells for (u32, u64) {
from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self>246     fn from_addr_cells(cells: &mut CellIterator, cell_count: AddrCells) -> Option<Self> {
247         Some(match cell_count {
248             AddrCells::Triple => {
249                 (cells.next()?, (cells.next()? as u64) << 32 | cells.next()? as u64)
250             }
251             _ => panic!("Invalid addr_cells {:?} for (u32, u64)", cell_count),
252         })
253     }
254 }
255 
256 trait FromSizeCells: Sized {
from_size_cells(cells: &mut CellIterator, cell_count: SizeCells) -> Option<Self>257     fn from_size_cells(cells: &mut CellIterator, cell_count: SizeCells) -> Option<Self>;
258 }
259 
260 impl FromSizeCells for u64 {
from_size_cells(cells: &mut CellIterator, cell_count: SizeCells) -> Option<Self>261     fn from_size_cells(cells: &mut CellIterator, cell_count: SizeCells) -> Option<Self> {
262         Some(match cell_count {
263             SizeCells::Single => cells.next()?.into(),
264             SizeCells::Double => (cells.next()? as Self) << 32 | cells.next()? as Self,
265             _ => panic!("Invalid size_cells {:?} for u64", cell_count),
266         })
267     }
268 }
269 
270 impl AddressRange<(u32, u64), u64, u64> {
271     const SIZE_CELLS: usize = 7;
272     /// Converts to the format that is consumable by libfdt
to_cells(&self) -> [u8; Self::SIZE_CELLS * size_of::<u32>()]273     pub fn to_cells(&self) -> [u8; Self::SIZE_CELLS * size_of::<u32>()] {
274         let buf = [
275             self.addr.0.to_be(),
276             ((self.addr.1 >> 32) as u32).to_be(),
277             (self.addr.1 as u32).to_be(),
278             ((self.parent_addr >> 32) as u32).to_be(),
279             (self.parent_addr as u32).to_be(),
280             ((self.size >> 32) as u32).to_be(),
281             (self.size as u32).to_be(),
282         ];
283 
284         transmute!(buf)
285     }
286 }
287 
288 /// Iterator over subnodes
289 #[derive(Debug)]
290 pub struct SubnodeIterator<'a> {
291     subnode: Option<FdtNode<'a>>,
292 }
293 
294 impl<'a> SubnodeIterator<'a> {
new(node: &FdtNode<'a>) -> Result<Self, FdtError>295     pub(crate) fn new(node: &FdtNode<'a>) -> Result<Self, FdtError> {
296         let subnode = node.first_subnode()?;
297 
298         Ok(Self { subnode })
299     }
300 }
301 
302 impl<'a> Iterator for SubnodeIterator<'a> {
303     type Item = FdtNode<'a>;
304 
next(&mut self) -> Option<Self::Item>305     fn next(&mut self) -> Option<Self::Item> {
306         let res = self.subnode;
307 
308         self.subnode = self.subnode.and_then(|node| node.next_subnode().ok()?);
309 
310         res
311     }
312 }
313 
314 /// Iterator over descendants
315 #[derive(Debug)]
316 pub struct DescendantsIterator<'a> {
317     node: Option<(FdtNode<'a>, usize)>,
318 }
319 
320 impl<'a> DescendantsIterator<'a> {
new(node: &FdtNode<'a>) -> Self321     pub(crate) fn new(node: &FdtNode<'a>) -> Self {
322         Self { node: Some((*node, 0)) }
323     }
324 }
325 
326 impl<'a> Iterator for DescendantsIterator<'a> {
327     type Item = (FdtNode<'a>, usize);
328 
next(&mut self) -> Option<Self::Item>329     fn next(&mut self) -> Option<Self::Item> {
330         let (node, depth) = self.node?;
331         self.node = node.next_node(depth).ok().flatten().filter(|(_, depth)| *depth > 0);
332 
333         self.node
334     }
335 }
336 
337 /// Iterator over properties
338 #[derive(Debug)]
339 pub struct PropertyIterator<'a> {
340     prop: Option<FdtProperty<'a>>,
341 }
342 
343 impl<'a> PropertyIterator<'a> {
new(node: &'a FdtNode) -> Result<Self, FdtError>344     pub(crate) fn new(node: &'a FdtNode) -> Result<Self, FdtError> {
345         let prop = node.first_property()?;
346 
347         Ok(Self { prop })
348     }
349 }
350 
351 impl<'a> Iterator for PropertyIterator<'a> {
352     type Item = FdtProperty<'a>;
353 
next(&mut self) -> Option<Self::Item>354     fn next(&mut self) -> Option<Self::Item> {
355         let res = self.prop;
356 
357         self.prop = res?.next_property().ok()?;
358 
359         res
360     }
361 }
362