1*5225e6b1SAndroid Build Coastguard Worker // Copyright 2024, The Android Open Source Project 2*5225e6b1SAndroid Build Coastguard Worker // 3*5225e6b1SAndroid Build Coastguard Worker // Licensed under the Apache License, Version 2.0 (the "License"); 4*5225e6b1SAndroid Build Coastguard Worker // you may not use this file except in compliance with the License. 5*5225e6b1SAndroid Build Coastguard Worker // You may obtain a copy of the License at 6*5225e6b1SAndroid Build Coastguard Worker // 7*5225e6b1SAndroid Build Coastguard Worker // http://www.apache.org/licenses/LICENSE-2.0 8*5225e6b1SAndroid Build Coastguard Worker // 9*5225e6b1SAndroid Build Coastguard Worker // Unless required by applicable law or agreed to in writing, software 10*5225e6b1SAndroid Build Coastguard Worker // distributed under the License is distributed on an "AS IS" BASIS, 11*5225e6b1SAndroid Build Coastguard Worker // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12*5225e6b1SAndroid Build Coastguard Worker // See the License for the specific language governing permissions and 13*5225e6b1SAndroid Build Coastguard Worker // limitations under the License. 14*5225e6b1SAndroid Build Coastguard Worker 15*5225e6b1SAndroid Build Coastguard Worker //! Selective implementation of APIs from crate `heapless` 0.8.0 using alloc. 16*5225e6b1SAndroid Build Coastguard Worker //! https://docs.rs/heapless/0.8.0/heapless/index.html 17*5225e6b1SAndroid Build Coastguard Worker //! 18*5225e6b1SAndroid Build Coastguard Worker //! The smoltcp crate depends on crate heapless. At the time this is written, the crate is either 19*5225e6b1SAndroid Build Coastguard Worker //! still in the process of being imported to Android or abandoned. Since we only use them in the 20*5225e6b1SAndroid Build Coastguard Worker //! EFI build which has alloc, we use a naive implementation of the needed APIs using heap 21*5225e6b1SAndroid Build Coastguard Worker //! allocation as a workaround for now. 22*5225e6b1SAndroid Build Coastguard Worker 23*5225e6b1SAndroid Build Coastguard Worker #![no_std] 24*5225e6b1SAndroid Build Coastguard Worker #![no_main] 25*5225e6b1SAndroid Build Coastguard Worker 26*5225e6b1SAndroid Build Coastguard Worker use core::ops::{Deref, DerefMut}; 27*5225e6b1SAndroid Build Coastguard Worker 28*5225e6b1SAndroid Build Coastguard Worker extern crate alloc; 29*5225e6b1SAndroid Build Coastguard Worker use alloc::collections::BTreeMap; 30*5225e6b1SAndroid Build Coastguard Worker use alloc::vec::Vec as AllocVec; 31*5225e6b1SAndroid Build Coastguard Worker 32*5225e6b1SAndroid Build Coastguard Worker /// `heapless::Vec` 33*5225e6b1SAndroid Build Coastguard Worker #[derive(Debug, PartialEq, Eq, Clone)] 34*5225e6b1SAndroid Build Coastguard Worker pub struct Vec<T, const N: usize>(AllocVec<T>); 35*5225e6b1SAndroid Build Coastguard Worker 36*5225e6b1SAndroid Build Coastguard Worker impl<T, const N: usize> Vec<T, N> { new() -> Self37*5225e6b1SAndroid Build Coastguard Worker pub fn new() -> Self { 38*5225e6b1SAndroid Build Coastguard Worker Self(AllocVec::new()) 39*5225e6b1SAndroid Build Coastguard Worker } 40*5225e6b1SAndroid Build Coastguard Worker capacity(&self) -> usize41*5225e6b1SAndroid Build Coastguard Worker pub fn capacity(&self) -> usize { 42*5225e6b1SAndroid Build Coastguard Worker N 43*5225e6b1SAndroid Build Coastguard Worker } 44*5225e6b1SAndroid Build Coastguard Worker push(&mut self, item: T) -> Result<(), T>45*5225e6b1SAndroid Build Coastguard Worker pub fn push(&mut self, item: T) -> Result<(), T> { 46*5225e6b1SAndroid Build Coastguard Worker match self.0.len() < N { 47*5225e6b1SAndroid Build Coastguard Worker true => { 48*5225e6b1SAndroid Build Coastguard Worker self.0.push(item); 49*5225e6b1SAndroid Build Coastguard Worker Ok(()) 50*5225e6b1SAndroid Build Coastguard Worker } 51*5225e6b1SAndroid Build Coastguard Worker _ => Err(item), 52*5225e6b1SAndroid Build Coastguard Worker } 53*5225e6b1SAndroid Build Coastguard Worker } 54*5225e6b1SAndroid Build Coastguard Worker } 55*5225e6b1SAndroid Build Coastguard Worker 56*5225e6b1SAndroid Build Coastguard Worker impl<T, const N: usize> Deref for Vec<T, N> { 57*5225e6b1SAndroid Build Coastguard Worker type Target = AllocVec<T>; 58*5225e6b1SAndroid Build Coastguard Worker deref(&self) -> &Self::Target59*5225e6b1SAndroid Build Coastguard Worker fn deref(&self) -> &Self::Target { 60*5225e6b1SAndroid Build Coastguard Worker &self.0 61*5225e6b1SAndroid Build Coastguard Worker } 62*5225e6b1SAndroid Build Coastguard Worker } 63*5225e6b1SAndroid Build Coastguard Worker 64*5225e6b1SAndroid Build Coastguard Worker impl<T, const N: usize> DerefMut for Vec<T, N> { deref_mut(&mut self) -> &mut Self::Target65*5225e6b1SAndroid Build Coastguard Worker fn deref_mut(&mut self) -> &mut Self::Target { 66*5225e6b1SAndroid Build Coastguard Worker &mut self.0 67*5225e6b1SAndroid Build Coastguard Worker } 68*5225e6b1SAndroid Build Coastguard Worker } 69*5225e6b1SAndroid Build Coastguard Worker 70*5225e6b1SAndroid Build Coastguard Worker impl<'a, T, const N: usize> IntoIterator for &'a Vec<T, N> { 71*5225e6b1SAndroid Build Coastguard Worker type Item = &'a T; 72*5225e6b1SAndroid Build Coastguard Worker type IntoIter = core::slice::Iter<'a, T>; 73*5225e6b1SAndroid Build Coastguard Worker into_iter(self) -> Self::IntoIter74*5225e6b1SAndroid Build Coastguard Worker fn into_iter(self) -> Self::IntoIter { 75*5225e6b1SAndroid Build Coastguard Worker self.0.iter() 76*5225e6b1SAndroid Build Coastguard Worker } 77*5225e6b1SAndroid Build Coastguard Worker } 78*5225e6b1SAndroid Build Coastguard Worker 79*5225e6b1SAndroid Build Coastguard Worker /// `heapless::LinearMap` 80*5225e6b1SAndroid Build Coastguard Worker #[derive(Debug, PartialEq, Eq, Clone)] 81*5225e6b1SAndroid Build Coastguard Worker pub struct LinearMap<K, V, const N: usize>(BTreeMap<K, V>); 82*5225e6b1SAndroid Build Coastguard Worker 83*5225e6b1SAndroid Build Coastguard Worker impl<K: core::cmp::Ord, V, const N: usize> LinearMap<K, V, N> { new() -> Self84*5225e6b1SAndroid Build Coastguard Worker pub fn new() -> Self { 85*5225e6b1SAndroid Build Coastguard Worker Self(BTreeMap::new()) 86*5225e6b1SAndroid Build Coastguard Worker } 87*5225e6b1SAndroid Build Coastguard Worker capacity(&self) -> usize88*5225e6b1SAndroid Build Coastguard Worker pub fn capacity(&self) -> usize { 89*5225e6b1SAndroid Build Coastguard Worker N 90*5225e6b1SAndroid Build Coastguard Worker } 91*5225e6b1SAndroid Build Coastguard Worker insert(&mut self, key: K, value: V) -> Result<Option<V>, (K, V)>92*5225e6b1SAndroid Build Coastguard Worker pub fn insert(&mut self, key: K, value: V) -> Result<Option<V>, (K, V)> { 93*5225e6b1SAndroid Build Coastguard Worker match self.0.len() < N { 94*5225e6b1SAndroid Build Coastguard Worker true => Ok(self.0.insert(key, value)), 95*5225e6b1SAndroid Build Coastguard Worker _ => Err((key, value)), 96*5225e6b1SAndroid Build Coastguard Worker } 97*5225e6b1SAndroid Build Coastguard Worker } 98*5225e6b1SAndroid Build Coastguard Worker } 99*5225e6b1SAndroid Build Coastguard Worker 100*5225e6b1SAndroid Build Coastguard Worker impl<K, V, const N: usize> Deref for LinearMap<K, V, N> { 101*5225e6b1SAndroid Build Coastguard Worker type Target = BTreeMap<K, V>; 102*5225e6b1SAndroid Build Coastguard Worker deref(&self) -> &Self::Target103*5225e6b1SAndroid Build Coastguard Worker fn deref(&self) -> &Self::Target { 104*5225e6b1SAndroid Build Coastguard Worker &self.0 105*5225e6b1SAndroid Build Coastguard Worker } 106*5225e6b1SAndroid Build Coastguard Worker } 107*5225e6b1SAndroid Build Coastguard Worker 108*5225e6b1SAndroid Build Coastguard Worker impl<K, V, const N: usize> DerefMut for LinearMap<K, V, N> { deref_mut(&mut self) -> &mut Self::Target109*5225e6b1SAndroid Build Coastguard Worker fn deref_mut(&mut self) -> &mut Self::Target { 110*5225e6b1SAndroid Build Coastguard Worker &mut self.0 111*5225e6b1SAndroid Build Coastguard Worker } 112*5225e6b1SAndroid Build Coastguard Worker } 113