use crate::parser::ast::*;
use crate::types::*;
+ use fxhash::FxBuildHasher;
use indexmap::IndexMap;
use std::collections::VecDeque;
IndexingCodePtr,
IndexingCodePtr,
),
- SwitchOnConstant(IndexMap<Literal, IndexingCodePtr>),
- SwitchOnStructure(IndexMap<(Atom, usize), IndexingCodePtr>),
+ SwitchOnConstant(IndexMap<Literal, IndexingCodePtr, FxBuildHasher>),
+ SwitchOnStructure(IndexMap<(Atom, usize), IndexingCodePtr, FxBuildHasher>),
}
#[derive(Debug, Clone, Copy)]
impl F64Table {
#[inline]
pub fn new() -> Self {
- F64Table { block: RawBlock::new() }
+ let table = Self { block: RawBlock::new() };
+ set_f64_tbl_buf_base(table.block.base);
+ table
}
pub unsafe fn build_with(&mut self, value: f64) -> F64Ptr {
}
}
- ptr::write(ptr as *mut f64, value);
+ ptr::write(ptr as *mut OrderedFloat<f64>, OrderedFloat(value));
F64Ptr(ptr::NonNull::new_unchecked(ptr as *mut _))
}
}
Self: Sized;
}
-#[derive(Copy, Clone, Debug, Hash, PartialEq, Eq, PartialOrd, Ord)]
+#[derive(Copy, Clone, Debug)]
pub struct F64Ptr(pub ptr::NonNull<OrderedFloat<f64>>);
+impl PartialEq for F64Ptr {
+ fn eq(&self, other: &F64Ptr) -> bool {
+ self.0 == other.0 || &**self == &**other
+ }
+}
+
+impl Eq for F64Ptr {}
+
+impl PartialOrd for F64Ptr {
+ fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering> {
+ (**self).partial_cmp(&**other)
+ }
+}
+
+impl Ord for F64Ptr {
+ fn cmp(&self, other: &Self) -> std::cmp::Ordering {
+ (**self).cmp(&**other)
+ }
+}
+
+impl Hash for F64Ptr {
+ #[inline(always)]
+ fn hash<H: Hasher>(&self, hasher: &mut H) {
+ (&*self as &OrderedFloat<f64>).hash(hasher)
+ }
+}
+
impl fmt::Display for F64Ptr {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{}", *self)
}
#[inline(always)]
- pub fn as_offset(&self) -> usize {
- self.0.as_ptr() as usize - get_f64_tbl_buf_base() as usize
+ pub fn as_offset(&self) -> F64Offset {
+ F64Offset(self.0.as_ptr() as usize - get_f64_tbl_buf_base() as usize)
+ }
+}
+
+#[derive(Clone, Copy, Debug)]
+pub struct F64Offset(usize);
+
+impl F64Offset {
+ #[inline(always)]
+ pub fn new(offset: usize) -> Self {
+ Self(offset)
+ }
+
+ #[inline(always)]
+ pub fn from_ptr(ptr: F64Ptr) -> Self {
+ ptr.as_offset()
+ }
+
+ #[inline(always)]
+ pub fn as_ptr(self) -> F64Ptr {
+ F64Ptr::from_offset(self.0)
+ }
+
+ #[inline(always)]
+ pub fn to_u64(self) -> u64 {
+ self.0 as u64
+ }
+}
+
+impl PartialEq for F64Offset {
+ #[inline(always)]
+ fn eq(&self, other: &F64Offset) -> bool {
+ self.as_ptr() == other.as_ptr()
+ }
+}
+
+impl Eq for F64Offset {}
+
+impl PartialOrd for F64Offset {
+ #[inline(always)]
+ fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering> {
+ self.as_ptr().partial_cmp(&other.as_ptr())
+ }
+}
+
+impl Ord for F64Offset {
+ #[inline(always)]
+ fn cmp(&self, other: &Self) -> std::cmp::Ordering {
+ self.as_ptr().cmp(&other.as_ptr())
+ }
+}
+
+impl Hash for F64Offset {
+ #[inline(always)]
+ fn hash<H: Hasher>(&self, hasher: &mut H) {
+ self.as_ptr().hash(hasher)
+ }
+}
+
+impl fmt::Display for F64Offset {
+ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+ write!(f, "F64Offset({})", self.0)
}
}
match c {
Literal::Fixnum(n) => interm.push(ArithmeticTerm::Number(Number::Fixnum(*n))),
Literal::Integer(n) => interm.push(ArithmeticTerm::Number(Number::Integer(*n))),
- Literal::Float(n) => interm.push(ArithmeticTerm::Number(Number::Float(**n))),
+ Literal::Float(n) => interm.push(ArithmeticTerm::Number(Number::Float(*n.as_ptr()))),
Literal::Rational(n) => interm.push(ArithmeticTerm::Number(Number::Rational(*n))),
Literal::Atom(name) if name == &atom!("e") => interm.push(ArithmeticTerm::Number(
Number::Float(OrderedFloat(std::f64::consts::E))
match value {
Number::Fixnum(n) => Literal::Fixnum(n),
Number::Integer(n) => Literal::Integer(n),
- Number::Float(OrderedFloat(f)) => Literal::Float(float_alloc!(f, arena)),
+ Number::Float(OrderedFloat(f)) => Literal::from(float_alloc!(f, arena)),
Number::Rational(r) => Literal::Rational(r),
}
}
use crate::forms::*;
use crate::instructions::*;
+use fxhash::FxBuildHasher;
use indexmap::IndexMap;
use std::collections::VecDeque;
self.append_or_prepend,
);
- let mut constants = IndexMap::new();
+ let mut constants = IndexMap::with_hasher(FxBuildHasher::default());
match constant_key {
Some(OptArgIndexKey::Literal(_, _, constant, _)) => {
break;
}
IndexingCodePtr::DynamicExternal(_) | IndexingCodePtr::External(_) => {
- let mut constants = IndexMap::new();
+ let mut constants = IndexMap::with_hasher(FxBuildHasher::default());
constants.insert(orig_constant, *c);
*c = IndexingCodePtr::Internal(indexing_code_len);
self.append_or_prepend,
);
- let mut structures = IndexMap::new();
+ let mut structures = IndexMap::with_hasher(FxBuildHasher::default());
match structure_key {
Some(OptArgIndexKey::Structure(_, _, name, arity)) => {
}).unwrap();
}
}
- /*
- Literal::Usize(n) => {
- constants.push(Literal::Integer(Rc::new(Integer::from(*n))));
-
- if let Ok(n) = isize::try_from(*n) {
- constants.push(Literal::Fixnum(n));
- }
- }
- */
_ => {}
}
#[derive(Debug)]
pub(crate) struct StaticCodeIndices {
- constants: IndexMap<Literal, VecDeque<IndexedChoiceInstruction>>,
+ constants: IndexMap<Literal, VecDeque<IndexedChoiceInstruction>, FxBuildHasher>,
lists: VecDeque<IndexedChoiceInstruction>,
- structures: IndexMap<(Atom, usize), VecDeque<IndexedChoiceInstruction>>,
+ structures: IndexMap<(Atom, usize), VecDeque<IndexedChoiceInstruction>, FxBuildHasher>,
}
#[derive(Debug)]
pub(crate) struct DynamicCodeIndices {
- constants: IndexMap<Literal, VecDeque<usize>>,
+ constants: IndexMap<Literal, VecDeque<usize>, FxBuildHasher>,
lists: VecDeque<usize>,
- structures: IndexMap<(Atom, usize), VecDeque<usize>>,
+ structures: IndexMap<(Atom, usize), VecDeque<usize>, FxBuildHasher>,
}
pub(crate) trait Indexer {
fn new() -> Self;
- fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<Self::ThirdLevelIndex>>;
+ fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<Self::ThirdLevelIndex>, FxBuildHasher>;
fn lists(&mut self) -> &mut VecDeque<Self::ThirdLevelIndex>;
- fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<Self::ThirdLevelIndex>>;
+ fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<Self::ThirdLevelIndex>, FxBuildHasher>;
fn compute_index(is_initial_index: bool, index: usize) -> Self::ThirdLevelIndex;
fn second_level_index<IndexKey: Eq + Hash>(
- indices: IndexMap<IndexKey, VecDeque<Self::ThirdLevelIndex>>,
+ indices: IndexMap<IndexKey, VecDeque<Self::ThirdLevelIndex>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
- ) -> IndexMap<IndexKey, IndexingCodePtr>;
+ ) -> IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher>;
fn switch_on<IndexKey: Eq + Hash>(
- instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr>) -> IndexingInstruction,
- index: &mut IndexMap<IndexKey, VecDeque<Self::ThirdLevelIndex>>,
+ instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher>) -> IndexingInstruction,
+ index: &mut IndexMap<IndexKey, VecDeque<Self::ThirdLevelIndex>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
) -> IndexingCodePtr;
#[inline]
fn new() -> Self {
Self {
- constants: IndexMap::new(),
+ constants: IndexMap::with_hasher(FxBuildHasher::default()),
lists: VecDeque::new(),
- structures: IndexMap::new(),
+ structures: IndexMap::with_hasher(FxBuildHasher::default()),
}
}
#[inline]
- fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<IndexedChoiceInstruction>> {
+ fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<IndexedChoiceInstruction>, FxBuildHasher> {
&mut self.constants
}
}
#[inline]
- fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<IndexedChoiceInstruction>> {
+ fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<IndexedChoiceInstruction>, FxBuildHasher> {
&mut self.structures
}
}
fn second_level_index<IndexKey: Eq + Hash>(
- indices: IndexMap<IndexKey, VecDeque<IndexedChoiceInstruction>>,
+ indices: IndexMap<IndexKey, VecDeque<IndexedChoiceInstruction>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
- ) -> IndexMap<IndexKey, IndexingCodePtr> {
- let mut index_locs = IndexMap::new();
+ ) -> IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher> {
+ let mut index_locs = IndexMap::with_hasher(FxBuildHasher::default());
for (key, mut code) in indices.into_iter() {
if code.len() > 1 {
}
fn switch_on<IndexKey: Eq + Hash>(
- mut instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr>) -> IndexingInstruction,
- index: &mut IndexMap<IndexKey, VecDeque<IndexedChoiceInstruction>>,
+ mut instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher>) -> IndexingInstruction,
+ index: &mut IndexMap<IndexKey, VecDeque<IndexedChoiceInstruction>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
) -> IndexingCodePtr {
- let index = mem::replace(index, IndexMap::new());
+ let index = mem::replace(index, IndexMap::with_hasher(FxBuildHasher::default()));
let index = Self::second_level_index(index, prelude);
if index.len() > 1 {
#[inline]
fn new() -> Self {
Self {
- constants: IndexMap::new(),
+ constants: IndexMap::with_hasher(FxBuildHasher::default()),
lists: VecDeque::new(),
- structures: IndexMap::new(),
+ structures: IndexMap::with_hasher(FxBuildHasher::default()),
}
}
#[inline]
- fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<usize>> {
+ fn constants(&mut self) -> &mut IndexMap<Literal, VecDeque<usize>, FxBuildHasher> {
&mut self.constants
}
}
#[inline]
- fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<usize>> {
+ fn structures(&mut self) -> &mut IndexMap<(Atom, usize), VecDeque<usize>, FxBuildHasher> {
&mut self.structures
}
}
fn second_level_index<IndexKey: Eq + Hash>(
- indices: IndexMap<IndexKey, VecDeque<usize>>,
+ indices: IndexMap<IndexKey, VecDeque<usize>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
- ) -> IndexMap<IndexKey, IndexingCodePtr> {
- let mut index_locs = IndexMap::new();
+ ) -> IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher> {
+ let mut index_locs = IndexMap::with_hasher(FxBuildHasher::default());
for (key, code) in indices.into_iter() {
if code.len() > 1 {
}
fn switch_on<IndexKey: Eq + Hash>(
- mut instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr>) -> IndexingInstruction,
- index: &mut IndexMap<IndexKey, VecDeque<usize>>,
+ mut instr_fn: impl FnMut(IndexMap<IndexKey, IndexingCodePtr, FxBuildHasher>) -> IndexingInstruction,
+ index: &mut IndexMap<IndexKey, VecDeque<usize>, FxBuildHasher>,
prelude: &mut VecDeque<IndexingLine>,
) -> IndexingCodePtr {
- let index = mem::replace(index, IndexMap::new());
+ let index = mem::replace(index, IndexMap::with_hasher(FxBuildHasher::default()));
let index = Self::second_level_index(index, prelude);
if index.len() > 1 {
Literal::Fixnum(n)
}
(HeapCellValueTag::F64, f) => {
- Literal::Float(f)
+ Literal::Float(f.as_offset())
}
(HeapCellValueTag::Atom, (atom, arity)) => {
debug_assert_eq!(arity, 0);
Literal::Rational(bigint_ptr) => {
typed_arena_ptr_as_cell!(bigint_ptr)
}
- Literal::Float(f) => HeapCellValue::from(f),
+ Literal::Float(f) => HeapCellValue::from(f.as_ptr()),
Literal::String(s) => {
if s == atom!("") {
empty_list_as_cell!()
Ok(Literal::Fixnum(n))
}
(HeapCellValueTag::F64, f) => {
- Ok(Literal::Float(f))
+ Ok(Literal::Float(f.as_offset()))
}
(HeapCellValueTag::Cons, cons_ptr) => {
match_untyped_arena_ptr!(cons_ptr,
self.unify_rational(n, nx);
}
Ok(Term::Literal(_, Literal::Float(n))) => {
- self.unify_f64(n, nx);
+ self.unify_f64(n.as_ptr(), nx);
}
Ok(Term::Literal(_, Literal::Integer(n))) => {
self.unify_big_int(n, nx);
Fixnum(Fixnum),
Integer(TypedArenaPtr<Integer>),
Rational(TypedArenaPtr<Rational>),
- Float(F64Ptr),
+ Float(F64Offset),
String(Atom),
}
+impl From<F64Ptr> for Literal {
+ #[inline(always)]
+ fn from(ptr: F64Ptr) -> Literal {
+ Literal::Float(ptr.as_offset())
+ }
+}
+
impl fmt::Display for Literal {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
fn vacate_with_float(&mut self, mut token: String) -> Result<Token, ParserError> {
self.return_char(token.pop().unwrap());
let n = parse_lossy::<f64, _>(token.as_bytes())?;
- Ok(Token::Literal(Literal::Float(float_alloc!(n, self.machine_st.arena))))
+ Ok(Token::Literal(Literal::from(float_alloc!(n, self.machine_st.arena))))
}
fn skip_underscore_in_number(&mut self) -> Result<char, ParserError> {
}
let n = parse_lossy::<f64, _>(token.as_bytes())?;
- Ok(Token::Literal(Literal::Float(
+ Ok(Token::Literal(Literal::from(
float_alloc!(n, self.machine_st.arena)
)))
} else {
}
} else {
let n = parse_lossy::<f64, _>(token.as_bytes())?;
- Ok(Token::Literal(Literal::Float(
+ Ok(Token::Literal(Literal::from(
float_alloc!(n, self.machine_st.arena)
)))
}
self.negate_number(n, negate_rc, |r, _| Literal::Rational(r))
}
Token::Literal(Literal::Float(n)) => self.negate_number(
- **n,
+ **n.as_ptr(),
|n| -n,
- |n, arena| Literal::Float(float_alloc!(n, arena))
+ |n, arena| Literal::from(float_alloc!(n, arena)),
),
Token::Literal(c) => {
if let Some(name) = atomize_constant(&mut self.lexer.machine_st.atom_tbl, c) {
}
}
- /*
- #[inline]
- pub fn take(&mut self) -> Self {
- mem::replace(self, Self::empty_block())
- }
- */
-
#[inline]
pub fn size(&self) -> usize {
self.top as usize - self.base as usize
impl fmt::Debug for HeapCellValue {
fn fmt(&self, f: &mut std::fmt::Formatter) -> fmt::Result {
match self.get_tag() {
- tag @ (HeapCellValueTag::Cons | HeapCellValueTag::F64) => {
+ HeapCellValueTag::F64 => {
+ f.debug_struct("HeapCellValue")
+ .field("tag", &HeapCellValueTag::F64)
+ .field("offset", &self.get_value())
+ .field("m", &self.m())
+ .field("f", &self.f())
+ .finish()
+ }
+ HeapCellValueTag::Cons => {
let cons_ptr = ConsPtr::from_bytes(self.into_bytes());
f.debug_struct("HeapCellValue")
- .field("tag", &tag)
+ .field("tag", &HeapCellValueTag::Cons)
.field("ptr", &cons_ptr.ptr())
.field("m", &cons_ptr.m())
+ .field("f", &cons_ptr.f())
.finish()
}
HeapCellValueTag::Atom => {
fn from(f64_ptr: F64Ptr) -> HeapCellValue {
HeapCellValue::build_with(
HeapCellValueTag::F64,
- f64_ptr.as_offset() as u64,
+ f64_ptr.as_offset().to_u64(),
)
}
}