support module resolution in current_predicate/1 (#1817)
This commit is contained in:
@@ -308,7 +308,7 @@ enum SystemClauseType {
|
|||||||
GetContinuationChunk,
|
GetContinuationChunk,
|
||||||
#[strum_discriminants(strum(props(Arity = "7", Name = "$get_next_op_db_ref")))]
|
#[strum_discriminants(strum(props(Arity = "7", Name = "$get_next_op_db_ref")))]
|
||||||
GetNextOpDBRef,
|
GetNextOpDBRef,
|
||||||
#[strum_discriminants(strum(props(Arity = "2", Name = "$lookup_db_ref")))]
|
#[strum_discriminants(strum(props(Arity = "3", Name = "$lookup_db_ref")))]
|
||||||
LookupDBRef,
|
LookupDBRef,
|
||||||
#[strum_discriminants(strum(props(Arity = "1", Name = "$is_partial_string")))]
|
#[strum_discriminants(strum(props(Arity = "1", Name = "$is_partial_string")))]
|
||||||
IsPartialString,
|
IsPartialString,
|
||||||
@@ -578,7 +578,7 @@ enum SystemClauseType {
|
|||||||
DeleteAllAttributesFromVar,
|
DeleteAllAttributesFromVar,
|
||||||
#[strum_discriminants(strum(props(Arity = "1", Name = "$unattributed_var")))]
|
#[strum_discriminants(strum(props(Arity = "1", Name = "$unattributed_var")))]
|
||||||
UnattributedVar,
|
UnattributedVar,
|
||||||
#[strum_discriminants(strum(props(Arity = "3", Name = "$get_db_refs")))]
|
#[strum_discriminants(strum(props(Arity = "4", Name = "$get_db_refs")))]
|
||||||
GetDBRefs,
|
GetDBRefs,
|
||||||
REPL(REPLCodePtr),
|
REPL(REPLCodePtr),
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1254,7 +1254,13 @@ current_predicate(Pred) :-
|
|||||||
( var(Pred) ->
|
( var(Pred) ->
|
||||||
'$get_db_refs'(_, _, PIs),
|
'$get_db_refs'(_, _, PIs),
|
||||||
lists:member(Pred, PIs)
|
lists:member(Pred, PIs)
|
||||||
; Pred = Name/Arity ->
|
; '$strip_module'(Pred, Module, UnqualifiedPred),
|
||||||
|
( var(Module),
|
||||||
|
\+ functor(Pred, (:), 2)
|
||||||
|
; atom(Module)
|
||||||
|
),
|
||||||
|
nonvar(UnqualifiedPred),
|
||||||
|
UnqualifiedPred = Name/Arity ->
|
||||||
( ( nonvar(Name), \+ atom(Name)
|
( ( nonvar(Name), \+ atom(Name)
|
||||||
; nonvar(Arity), \+ integer(Arity)
|
; nonvar(Arity), \+ integer(Arity)
|
||||||
; integer(Arity), Arity < 0
|
; integer(Arity), Arity < 0
|
||||||
@@ -1262,9 +1268,9 @@ current_predicate(Pred) :-
|
|||||||
throw(error(type_error(predicate_indicator, Pred), current_predicate/1))
|
throw(error(type_error(predicate_indicator, Pred), current_predicate/1))
|
||||||
; nonvar(Name),
|
; nonvar(Name),
|
||||||
nonvar(Arity) ->
|
nonvar(Arity) ->
|
||||||
'$lookup_db_ref'(Name, Arity)
|
'$lookup_db_ref'(Module, Name, Arity)
|
||||||
; '$get_db_refs'(Name, Arity, PIs),
|
; '$get_db_refs'(Module, Name, Arity, PIs),
|
||||||
lists:member(Pred, PIs)
|
lists:member(UnqualifiedPred, PIs)
|
||||||
)
|
)
|
||||||
; throw(error(type_error(predicate_indicator, Pred), current_predicate/1))
|
; throw(error(type_error(predicate_indicator, Pred), current_predicate/1))
|
||||||
).
|
).
|
||||||
|
|||||||
@@ -227,7 +227,6 @@ impl CodeIndex {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) type HeapVarDict = IndexMap<VarPtr, HeapCellValue, FxBuildHasher>;
|
pub(crate) type HeapVarDict = IndexMap<VarPtr, HeapCellValue, FxBuildHasher>;
|
||||||
// pub(crate) type AllocVarDict = IndexMap<Var, VarAlloc, FxBuildHasher>;
|
|
||||||
|
|
||||||
pub(crate) type GlobalVarDir = IndexMap<Atom, (Ball, Option<HeapCellValue>), FxBuildHasher>;
|
pub(crate) type GlobalVarDir = IndexMap<Atom, (Ball, Option<HeapCellValue>), FxBuildHasher>;
|
||||||
|
|
||||||
|
|||||||
@@ -3744,12 +3744,25 @@ impl Machine {
|
|||||||
|
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub(crate) fn lookup_db_ref(&mut self) {
|
pub(crate) fn lookup_db_ref(&mut self) {
|
||||||
let name = cell_as_atom!(self.deref_register(1));
|
let module_name = self.deref_register(1);
|
||||||
let arity = cell_as_fixnum!(self.deref_register(2)).get_num() as usize;
|
let name = cell_as_atom!(self.deref_register(2));
|
||||||
|
let arity = cell_as_fixnum!(self.deref_register(3)).get_num() as usize;
|
||||||
|
|
||||||
if self.indices.code_dir.get(&(name, arity)).is_none() {
|
let module_name = read_heap_cell!(module_name,
|
||||||
self.machine_st.fail = true;
|
(HeapCellValueTag::Atom, (module_name, _arity)) => {
|
||||||
}
|
module_name
|
||||||
|
}
|
||||||
|
(HeapCellValueTag::AttrVar | HeapCellValueTag::Var) => {
|
||||||
|
atom!("user")
|
||||||
|
}
|
||||||
|
_ => {
|
||||||
|
unreachable!()
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
self.machine_st.fail = self.indices
|
||||||
|
.get_predicate_code_index(name, arity, module_name)
|
||||||
|
.is_none();
|
||||||
}
|
}
|
||||||
|
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
@@ -3757,7 +3770,19 @@ impl Machine {
|
|||||||
let name_match: fn(Atom, Atom) -> bool;
|
let name_match: fn(Atom, Atom) -> bool;
|
||||||
let arity_match: fn(usize, usize) -> bool;
|
let arity_match: fn(usize, usize) -> bool;
|
||||||
|
|
||||||
let atom = self.deref_register(1);
|
let module_name = read_heap_cell!(self.deref_register(1),
|
||||||
|
(HeapCellValueTag::Atom, (module_name, _arity)) => {
|
||||||
|
module_name
|
||||||
|
}
|
||||||
|
(HeapCellValueTag::AttrVar | HeapCellValueTag::Var) => {
|
||||||
|
atom!("user")
|
||||||
|
}
|
||||||
|
_ => {
|
||||||
|
unreachable!()
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
let atom = self.deref_register(2);
|
||||||
|
|
||||||
let pred_atom = if atom.is_var() {
|
let pred_atom = if atom.is_var() {
|
||||||
name_match = |_, _| true;
|
name_match = |_, _| true;
|
||||||
@@ -3767,7 +3792,7 @@ impl Machine {
|
|||||||
cell_as_atom!(atom)
|
cell_as_atom!(atom)
|
||||||
};
|
};
|
||||||
|
|
||||||
let arity = self.deref_register(2);
|
let arity = self.deref_register(3);
|
||||||
|
|
||||||
let pred_arity = if arity.is_var() {
|
let pred_arity = if arity.is_var() {
|
||||||
arity_match = |_, _| true;
|
arity_match = |_, _| true;
|
||||||
@@ -3792,7 +3817,19 @@ impl Machine {
|
|||||||
let h = self.machine_st.heap.len();
|
let h = self.machine_st.heap.len();
|
||||||
let mut num_functors = 0;
|
let mut num_functors = 0;
|
||||||
|
|
||||||
for (name, arity) in self.indices.code_dir.keys() {
|
let code_dir = if module_name == atom!("user") {
|
||||||
|
&self.indices.code_dir
|
||||||
|
} else {
|
||||||
|
match self.indices.modules.get(&module_name).map(|module| &module.code_dir) {
|
||||||
|
Some(code_dir) => code_dir,
|
||||||
|
None => {
|
||||||
|
self.machine_st.fail = true;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
for (name, arity) in code_dir.keys() {
|
||||||
if name_match(pred_atom, *name) && arity_match(pred_arity, *arity) {
|
if name_match(pred_atom, *name) && arity_match(pred_arity, *arity) {
|
||||||
self.machine_st.heap.extend(
|
self.machine_st.heap.extend(
|
||||||
functor!(atom!("/"), [cell(atom_as_cell!(name)), fixnum(*arity)]),
|
functor!(atom!("/"), [cell(atom_as_cell!(name)), fixnum(*arity)]),
|
||||||
|
|||||||
Reference in New Issue
Block a user