From 1adf2ccf7553dbcb4fdcea4ed30c272589a6c828 Mon Sep 17 00:00:00 2001 From: overlookmotel Date: Wed, 21 Aug 2024 01:31:55 +0100 Subject: [PATCH] refactor(allocator): move `Box` and `Vec` into separate files --- .../oxc_allocator/src/{arena.rs => boxed.rs} | 140 +--------------- crates/oxc_allocator/src/lib.rs | 11 +- crates/oxc_allocator/src/vec.rs | 154 ++++++++++++++++++ 3 files changed, 168 insertions(+), 137 deletions(-) rename crates/oxc_allocator/src/{arena.rs => boxed.rs} (56%) create mode 100644 crates/oxc_allocator/src/vec.rs diff --git a/crates/oxc_allocator/src/arena.rs b/crates/oxc_allocator/src/boxed.rs similarity index 56% rename from crates/oxc_allocator/src/arena.rs rename to crates/oxc_allocator/src/boxed.rs index 643f3ec2bf8fc..a334d5cc1d9ac 100644 --- a/crates/oxc_allocator/src/arena.rs +++ b/crates/oxc_allocator/src/boxed.rs @@ -1,5 +1,6 @@ -//! Bumpalo memory arena utilities -//! Copied from [jsparagus](https://github.com/mozilla-spidermonkey/jsparagus/blob/master/crates/ast/src/arena.rs) +//! Arena Box. +//! +//! Originally based on [jsparagus](https://github.com/mozilla-spidermonkey/jsparagus/blob/master/crates/ast/src/arena.rs) use std::{ self, @@ -10,11 +11,8 @@ use std::{ ptr::{self, NonNull}, }; -use allocator_api2::vec; -pub use bumpalo::collections::String; -use bumpalo::Bump; #[cfg(any(feature = "serialize", test))] -use serde::{ser::SerializeSeq, Serialize, Serializer}; +use serde::{Serialize, Serializer}; use crate::Allocator; @@ -107,111 +105,6 @@ impl<'alloc, T: Hash> Hash for Box<'alloc, T> { } } -/// Bumpalo Vec -#[derive(Debug, PartialEq, Eq)] -pub struct Vec<'alloc, T>(vec::Vec); - -impl<'alloc, T> Vec<'alloc, T> { - #[inline] - pub fn new_in(allocator: &'alloc Allocator) -> Self { - Self(vec::Vec::new_in(allocator)) - } - - #[inline] - pub fn with_capacity_in(capacity: usize, allocator: &'alloc Allocator) -> Self { - Self(vec::Vec::with_capacity_in(capacity, allocator)) - } - - #[inline] - pub fn from_iter_in>(iter: I, allocator: &'alloc Allocator) -> Self { - let iter = iter.into_iter(); - let capacity = iter.size_hint().1.unwrap_or(0); - let mut vec = vec::Vec::with_capacity_in(capacity, &**allocator); - vec.extend(iter); - Self(vec) - } -} - -impl<'alloc, T> ops::Deref for Vec<'alloc, T> { - type Target = vec::Vec; - - fn deref(&self) -> &Self::Target { - &self.0 - } -} - -impl<'alloc, T> ops::DerefMut for Vec<'alloc, T> { - fn deref_mut(&mut self) -> &mut vec::Vec { - &mut self.0 - } -} - -impl<'alloc, T> IntoIterator for Vec<'alloc, T> { - type IntoIter = as IntoIterator>::IntoIter; - type Item = T; - - fn into_iter(self) -> Self::IntoIter { - self.0.into_iter() - } -} - -impl<'alloc, T> IntoIterator for &'alloc Vec<'alloc, T> { - type IntoIter = std::slice::Iter<'alloc, T>; - type Item = &'alloc T; - - fn into_iter(self) -> Self::IntoIter { - self.0.iter() - } -} - -impl<'alloc, T> ops::Index for Vec<'alloc, T> { - type Output = T; - - fn index(&self, index: usize) -> &Self::Output { - self.0.index(index) - } -} - -impl<'alloc, T> ops::Index for &'alloc Vec<'alloc, T> { - type Output = T; - - fn index(&self, index: usize) -> &Self::Output { - self.0.index(index) - } -} - -// Unused right now. -// impl<'alloc, T> ops::IndexMut for Vec<'alloc, T> { -// fn index_mut(&mut self, index: usize) -> &mut Self::Output { -// self.0.index_mut(index) -// } -// } - -#[cfg(any(feature = "serialize", test))] -impl<'alloc, T> Serialize for Vec<'alloc, T> -where - T: Serialize, -{ - fn serialize(&self, s: S) -> Result - where - S: Serializer, - { - let mut seq = s.serialize_seq(Some(self.0.len()))?; - for e in &self.0 { - seq.serialize_element(e)?; - } - seq.end() - } -} - -impl<'alloc, T: Hash> Hash for Vec<'alloc, T> { - fn hash(&self, state: &mut H) { - for e in &self.0 { - e.hash(state); - } - } -} - /// Memory address of an AST node in arena. /// /// `Address` is generated from a `Box`. @@ -231,7 +124,9 @@ impl<'a, T> Box<'a, T> { mod test { use std::hash::{DefaultHasher, Hash, Hasher}; - use crate::{Allocator, Box, Vec}; + use crate::Allocator; + + use super::Box; #[test] fn box_deref_mut() { @@ -265,15 +160,6 @@ mod test { assert_eq!(hash(&a), hash(&b)); } - #[test] - fn vec_debug() { - let allocator = Allocator::default(); - let mut v = Vec::new_in(&allocator); - v.push("x"); - let v = format!("{v:?}"); - assert_eq!(v, "Vec([\"x\"])"); - } - #[test] fn box_serialize() { let allocator = Allocator::default(); @@ -282,22 +168,10 @@ mod test { assert_eq!(b, "\"x\""); } - #[test] - fn vec_serialize() { - let allocator = Allocator::default(); - let mut v = Vec::new_in(&allocator); - v.push("x"); - let v = serde_json::to_string(&v).unwrap(); - assert_eq!(v, "[\"x\"]"); - } - #[test] fn lifetime_variance() { fn _assert_box_variant_lifetime<'a: 'b, 'b, T>(program: Box<'a, T>) -> Box<'b, T> { program } - fn _assert_vec_variant_lifetime<'a: 'b, 'b, T>(program: Vec<'a, T>) -> Vec<'b, T> { - program - } } } diff --git a/crates/oxc_allocator/src/lib.rs b/crates/oxc_allocator/src/lib.rs index 4093dd75ddffb..f6882c4bf0ee9 100644 --- a/crates/oxc_allocator/src/lib.rs +++ b/crates/oxc_allocator/src/lib.rs @@ -3,15 +3,18 @@ use std::{ ops::{Deref, DerefMut}, }; -mod arena; +pub use bumpalo::collections::String; +use bumpalo::Bump; + +mod boxed; mod clone_in; mod convert; +mod vec; -use bumpalo::Bump; - -pub use arena::{Address, Box, String, Vec}; +pub use boxed::{Address, Box}; pub use clone_in::CloneIn; pub use convert::{FromIn, IntoIn}; +pub use vec::Vec; #[derive(Default)] pub struct Allocator { diff --git a/crates/oxc_allocator/src/vec.rs b/crates/oxc_allocator/src/vec.rs new file mode 100644 index 0000000000000..a31e927c6e0ed --- /dev/null +++ b/crates/oxc_allocator/src/vec.rs @@ -0,0 +1,154 @@ +//! Arena Vec. +//! +//! Originally based on [jsparagus](https://github.com/mozilla-spidermonkey/jsparagus/blob/master/crates/ast/src/arena.rs) + +use std::{ + self, + fmt::Debug, + hash::{Hash, Hasher}, + ops, +}; + +use allocator_api2::vec; +use bumpalo::Bump; +#[cfg(any(feature = "serialize", test))] +use serde::{ser::SerializeSeq, Serialize, Serializer}; + +use crate::Allocator; + +/// Bumpalo Vec +#[derive(Debug, PartialEq, Eq)] +pub struct Vec<'alloc, T>(vec::Vec); + +impl<'alloc, T> Vec<'alloc, T> { + #[inline] + pub fn new_in(allocator: &'alloc Allocator) -> Self { + Self(vec::Vec::new_in(allocator)) + } + + #[inline] + pub fn with_capacity_in(capacity: usize, allocator: &'alloc Allocator) -> Self { + Self(vec::Vec::with_capacity_in(capacity, allocator)) + } + + #[inline] + pub fn from_iter_in>(iter: I, allocator: &'alloc Allocator) -> Self { + let iter = iter.into_iter(); + let capacity = iter.size_hint().1.unwrap_or(0); + let mut vec = vec::Vec::with_capacity_in(capacity, &**allocator); + vec.extend(iter); + Self(vec) + } +} + +impl<'alloc, T> ops::Deref for Vec<'alloc, T> { + type Target = vec::Vec; + + fn deref(&self) -> &Self::Target { + &self.0 + } +} + +impl<'alloc, T> ops::DerefMut for Vec<'alloc, T> { + fn deref_mut(&mut self) -> &mut vec::Vec { + &mut self.0 + } +} + +impl<'alloc, T> IntoIterator for Vec<'alloc, T> { + type IntoIter = as IntoIterator>::IntoIter; + type Item = T; + + fn into_iter(self) -> Self::IntoIter { + self.0.into_iter() + } +} + +impl<'alloc, T> IntoIterator for &'alloc Vec<'alloc, T> { + type IntoIter = std::slice::Iter<'alloc, T>; + type Item = &'alloc T; + + fn into_iter(self) -> Self::IntoIter { + self.0.iter() + } +} + +impl<'alloc, T> ops::Index for Vec<'alloc, T> { + type Output = T; + + fn index(&self, index: usize) -> &Self::Output { + self.0.index(index) + } +} + +impl<'alloc, T> ops::Index for &'alloc Vec<'alloc, T> { + type Output = T; + + fn index(&self, index: usize) -> &Self::Output { + self.0.index(index) + } +} + +// Unused right now. +// impl<'alloc, T> ops::IndexMut for Vec<'alloc, T> { +// fn index_mut(&mut self, index: usize) -> &mut Self::Output { +// self.0.index_mut(index) +// } +// } + +#[cfg(any(feature = "serialize", test))] +impl<'alloc, T> Serialize for Vec<'alloc, T> +where + T: Serialize, +{ + fn serialize(&self, s: S) -> Result + where + S: Serializer, + { + let mut seq = s.serialize_seq(Some(self.0.len()))?; + for e in &self.0 { + seq.serialize_element(e)?; + } + seq.end() + } +} + +impl<'alloc, T: Hash> Hash for Vec<'alloc, T> { + fn hash(&self, state: &mut H) { + for e in &self.0 { + e.hash(state); + } + } +} + +#[cfg(test)] +mod test { + use crate::Allocator; + + use super::Vec; + + #[test] + fn vec_debug() { + let allocator = Allocator::default(); + let mut v = Vec::new_in(&allocator); + v.push("x"); + let v = format!("{v:?}"); + assert_eq!(v, "Vec([\"x\"])"); + } + + #[test] + fn vec_serialize() { + let allocator = Allocator::default(); + let mut v = Vec::new_in(&allocator); + v.push("x"); + let v = serde_json::to_string(&v).unwrap(); + assert_eq!(v, "[\"x\"]"); + } + + #[test] + fn lifetime_variance() { + fn _assert_vec_variant_lifetime<'a: 'b, 'b, T>(program: Vec<'a, T>) -> Vec<'b, T> { + program + } + } +}