From: Mark Thom Date: Sat, 23 Jul 2022 19:16:02 +0000 (-0600) Subject: deduplicate index ptr inlining for 0-arity atoms (#1538) X-Git-Tag: v0.9.1^2~51 X-Git-Url: https://git.sagredo.dev/?a=commitdiff_plain;h=ea95a7900cabce03fc3ece6cea615583c9b062bb;p=scryer-prolog.git deduplicate index ptr inlining for 0-arity atoms (#1538) --- diff --git a/src/heap_iter.rs b/src/heap_iter.rs index f3b36334..9760be9e 100644 --- a/src/heap_iter.rs +++ b/src/heap_iter.rs @@ -351,12 +351,33 @@ impl Iterator for PostOrderIterator { } impl FocusedHeapIter for PostOrderIterator { - #[inline] + #[inline(always)] fn focus(&self) -> usize { self.focus } } +impl PostOrderIterator { + /* return true if the term at heap offset idx_loc is a + * direct/inlined subterm of a structure at the focus of + * self.stack.last(). this function is used to determine, e.g., + * ownership of inlined code indices. + */ + #[inline] + pub(crate) fn direct_subterm_of_str(&self, idx_loc: usize) -> bool { + if let Some((_child_count, item, focus)) = self.parent_stack.last() { + read_heap_cell!(item, + (HeapCellValueTag::Atom, (_name, arity)) => { + return focus + arity >= idx_loc && *focus < idx_loc; + } + _ => {} + ); + } + + false + } +} + pub(crate) type LeftistPostOrderHeapIter<'a> = PostOrderIterator>; impl<'a> LeftistPostOrderHeapIter<'a> { diff --git a/src/machine/loader.rs b/src/machine/loader.rs index 0cc93f50..7c9b380c 100644 --- a/src/machine/loader.rs +++ b/src/machine/loader.rs @@ -517,11 +517,17 @@ impl<'a, LS: LoadState<'a>> Loader<'a, LS> { let value = iter.heap[h + arity + 1]; if let Some(idx) = get_structure_index(value) { - term_stack.push( - Term::Literal(Cell::default(), Literal::CodeIndex(idx)) - ); + // in the second condition, arity == 0, + // meaning idx cannot pertain to this atom + // if it is the direct subterm of a larger + // structure. + if arity > 0 || !iter.direct_subterm_of_str(h) { + term_stack.push( + Term::Literal(Cell::default(), Literal::CodeIndex(idx)) + ); - arity += 1; + arity += 1; + } } }