Skip to content

Commit 10fb802

Browse files
authored
feat: expose arena public functions (#26)
1 parent 0cf03c8 commit 10fb802

2 files changed

Lines changed: 51 additions & 38 deletions

File tree

src/arena.rs

Lines changed: 38 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,14 @@ use rustc_hash::{FxBuildHasher, FxHashMap};
44
use serde::Serialize;
55
use std::collections::hash_map::Entry;
66
use std::hash::BuildHasher;
7+
use std::ops::Range;
78
use unicase::Ascii;
89

910
/// An arena-based allocator for interning strings.
1011
///
1112
/// Deduplicates strings by hash and returns lightweight [`StrRef`] handles for O(1) lookups.
1213
#[derive(Default, Serialize)]
13-
pub struct StringArena {
14+
pub(crate) struct StringArena {
1415
#[serde(skip_serializing)]
1516
hasher: FxBuildHasher,
1617

@@ -78,7 +79,7 @@ pub struct Expr {
7879
/// The `ExprArena` provides a memory-efficient way to store and manage AST nodes
7980
/// by using a flat vector and returning lightweight [`ExprRef`] handles.
8081
#[derive(Default, Serialize)]
81-
pub struct ExprArena {
82+
pub(crate) struct ExprArena {
8283
#[serde(skip_serializing)]
8384
hasher: FxBuildHasher,
8485
exprs: Vec<Expr>,
@@ -138,13 +139,13 @@ impl ExprArena {
138139
}
139140

140141
/// Returns an iterator over valid indices for the given [`VecRef`].
141-
pub fn vec_idxes(&self, ptr: VecRef) -> impl Iterator<Item = usize> + use<> {
142+
pub fn vec_idxes(&self, ptr: VecRef) -> Range<usize> {
142143
0..self.vec(ptr).len()
143144
}
144145

145146
/// Returns the vector of fields for the given [`RecRef`].
146-
pub fn rec(&self, ptr: RecRef) -> &Vec<Field> {
147-
&self.recs[ptr.0]
147+
pub fn rec(&self, ptr: RecRef) -> &[Field] {
148+
self.recs[ptr.0].as_slice()
148149
}
149150

150151
/// Returns the field at index `idx` within the given [`RecRef`].
@@ -153,7 +154,7 @@ impl ExprArena {
153154
}
154155

155156
/// Returns an iterator over valid indices for the given [`RecRef`].
156-
pub fn rec_idxes(&self, ptr: RecRef) -> impl Iterator<Item = usize> + use<> {
157+
pub fn rec_idxes(&self, ptr: RecRef) -> Range<usize> {
157158
0..self.rec(ptr).len()
158159
}
159160
}
@@ -163,7 +164,7 @@ impl ExprArena {
163164
/// Stores and deduplicates types, record definitions, and function argument lists.
164165
/// Supports freezing to mark a baseline and freeing types allocated after the baseline.
165166
#[derive(Default, Serialize)]
166-
pub struct TypeArena {
167+
pub(crate) struct TypeArena {
167168
#[serde(skip_serializing)]
168169
args_hasher: FxBuildHasher,
169170

@@ -267,11 +268,6 @@ impl TypeArena {
267268
self.args[key.0].as_slice()
268269
}
269270

270-
/// Returns a mutable reference to the argument type slice for the given [`ArgsRef`].
271-
pub fn get_args_mut(&mut self, key: ArgsRef) -> &mut [Type] {
272-
self.args[key.0].as_mut_slice()
273-
}
274-
275271
/// Returns an iterator over valid indices for the given [`ArgsRef`].
276272
pub fn args_idxes(&self, key: ArgsRef) -> impl Iterator<Item = usize> + use<> {
277273
0..self.get_args(key).len()
@@ -287,16 +283,6 @@ impl TypeArena {
287283
self.records[record.0].get(&field).copied()
288284
}
289285

290-
/// Iterates over all (field name, type) pairs in the given record.
291-
pub fn record_iter(&self, record: Record) -> impl Iterator<Item = (StrRef, Type)> {
292-
self.records[record.0].iter().map(|(k, v)| (*k, *v))
293-
}
294-
295-
/// Iterates over all field names in the given record.
296-
pub fn record_keys(&self, record: Record) -> impl Iterator<Item = StrRef> {
297-
self.records[record.0].keys().copied()
298-
}
299-
300286
/// Checks whether two records have the exact same set of field names.
301287
pub fn records_have_same_keys(&self, rec_a: Record, rec_b: Record) -> bool {
302288
let rec_a = self.get_record(rec_a);
@@ -324,16 +310,6 @@ impl TypeArena {
324310
self.alloc_record(FxHashMap::default())
325311
}
326312

327-
/// Returns `true` if the given field exists in the record.
328-
pub fn record_field_exists(&self, record: Record, field: StrRef) -> bool {
329-
self.records[record.0].contains_key(&field)
330-
}
331-
332-
/// Returns the hash map entry for a field in the given record, for in-place manipulation.
333-
pub fn record_entry(&mut self, record: Record, key: StrRef) -> Entry<'_, StrRef, Type> {
334-
self.records[record.0].entry(key)
335-
}
336-
337313
/// Sets the type of a field in the given record, inserting or updating as needed.
338314
pub fn record_set(&mut self, record: Record, field: StrRef, value: Type) {
339315
self.records[record.0].insert(field, value);
@@ -343,11 +319,6 @@ impl TypeArena {
343319
pub fn record_len(&self, record: Record) -> usize {
344320
self.records[record.0].len()
345321
}
346-
347-
/// Returns `true` if the given record has no fields.
348-
pub fn record_is_empty(&self, record: Record) -> bool {
349-
self.records[record.0].is_empty()
350-
}
351322
}
352323

353324
/// Top-level arena that holds all memory pools for expressions, strings, and types.
@@ -368,4 +339,34 @@ impl Arena {
368339
pub fn free_space(&mut self) {
369340
self.types.free_space();
370341
}
342+
343+
/// Retrieves the interned string associated with the given [`StrRef`].
344+
pub fn get_str(&self, key: StrRef) -> &str {
345+
self.strings.get(key)
346+
}
347+
348+
/// Retrieves the expression node associated with the given [`ExprRef`].
349+
pub fn get_expr(&self, key: ExprRef) -> Expr {
350+
self.exprs.get(key)
351+
}
352+
353+
/// Retrieves the type associated with the given [`TypeRef`].
354+
pub fn get_type(&self, key: TypeRef) -> Type {
355+
self.types.get_type(key)
356+
}
357+
358+
/// Returns the slice of expression references for the given [`VecRef`].
359+
pub fn get_vec(&self, key: VecRef) -> &[ExprRef] {
360+
self.exprs.vec(key)
361+
}
362+
363+
/// Returns the slice of record fields for the given [`RecRef`].
364+
pub fn get_rec(&self, key: RecRef) -> &[Field] {
365+
self.exprs.rec(key)
366+
}
367+
368+
/// Returns the function argument types for the given [`ArgsRef`].
369+
pub fn get_args(&self, key: ArgsRef) -> &[Type] {
370+
self.types.get_args(key)
371+
}
371372
}

src/lib.rs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,18 +16,20 @@ mod typing;
1616
use crate::arena::Arena;
1717
use crate::lexer::tokenize;
1818
use crate::prelude::{
19-
Analysis, AnalysisOptions, FunArgs, Type, Typed, display_type, name_to_type, parse,
19+
Analysis, AnalysisOptions, FunArgs, Typed, display_type, name_to_type, parse,
2020
};
2121
use crate::token::Token;
2222
pub use ast::*;
2323
use rustc_hash::FxHashMap;
24+
pub use typing::Type;
2425
use unicase::Ascii;
2526

2627
/// Convenience module that re-exports all public types and functions.
2728
///
2829
/// This module provides a single import point for all the library's public API,
2930
/// including AST types, error types, lexer, parser, and token types.
3031
pub mod prelude {
32+
pub use super::arena::*;
3133
pub use super::ast::*;
3234
pub use super::error::*;
3335
pub use super::parser::*;
@@ -569,4 +571,14 @@ impl Session {
569571
pub fn analysis(&mut self) -> Analysis<'_> {
570572
Analysis::new(&mut self.arena, &self.options)
571573
}
574+
575+
/// Returns a reference to the underlying [`Arena`].
576+
pub fn arena(&self) -> &Arena {
577+
&self.arena
578+
}
579+
580+
/// Returns a mutable reference to the underlying [`Arena`].
581+
pub fn arena_mut(&mut self) -> &mut Arena {
582+
&mut self.arena
583+
}
572584
}

0 commit comments

Comments
 (0)