address issues #114, #115

This commit is contained in:
Mark Thom
2019-04-25 09:10:52 -06:00
parent 18a9a6434f
commit b07a19fc47
5 changed files with 52 additions and 34 deletions

View File

@@ -1,6 +1,6 @@
[package]
name = "scryer-prolog"
version = "0.8.63"
version = "0.8.64"
authors = ["Mark Thom <markjordanthom@gmail.com>"]
repository = "https://github.com/mthom/scryer-prolog"
description = "A modern Prolog implementation written mostly in Rust."

View File

@@ -769,6 +769,7 @@ char_code(Char, Code) :-
get_char(C) :-
( var(C) -> '$get_char'(C)
; C == end_of_file -> '$get_char'(C)
; atom_length(C, 1) -> '$get_char'(C)
; throw(error(type_error(in_character, C), get_char/1))
).

View File

@@ -619,7 +619,7 @@ pub(crate) trait CallPolicy: Any {
return_from_clause!(machine_st.last_call, machine_st)
},
&BuiltInClauseType::Functor => {
machine_st.try_functor(&indices.op_dir)?;
machine_st.try_functor(&indices)?;
return_from_clause!(machine_st.last_call, machine_st)
},
&BuiltInClauseType::NotEq => {

View File

@@ -1,5 +1,6 @@
use prolog_parser::ast::*;
use prolog_parser::string_list::StringList;
use prolog_parser::tabled_rc::*;
use prolog::clause_types::*;
use prolog::forms::*;
@@ -191,7 +192,7 @@ impl MachineState {
-> Outputter
where Outputter: HCValueOutputter
{
let orig_len = output.len();
let orig_len = output.len();
output.begin_new_var();
@@ -204,7 +205,7 @@ impl MachineState {
printer.quoted = true;
let mut output = printer.print(addr);
let bad_ending = format!("= {}", &var);
if output.ends_with(&bad_ending) {
@@ -702,7 +703,7 @@ impl MachineState {
Ok(Rc::new(Ratio::from_integer((*bi).clone())))
}
}
fn get_rational(&mut self, at: &ArithmeticTerm, caller: &MachineStub)
-> Result<Rc<Ratio<BigInt>>, MachineStub>
{
@@ -857,12 +858,12 @@ impl MachineState {
(Number::Integer(_), n) | (n, _) => {
let n = Addr::Con(Constant::Number(n));
let stub = MachineError::functor_stub(clause_name!("^"), 2);
Err(self.error_form(MachineError::type_error(ValidType::Integer, n), stub))
Err(self.error_form(MachineError::type_error(ValidType::Integer, n), stub))
}
}
}
fn pow(&self, n1: Number, n2: Number) -> Result<Number, MachineStub>
{
match n1.pow(n2) {
@@ -2049,7 +2050,29 @@ impl MachineState {
self.try_functor_unify_components(name, arity);
}
pub(super) fn try_functor(&mut self, op_dir: &OpDir) -> CallResult {
fn try_functor_fabricate_struct(&mut self, name: ClauseName, arity: isize,
spec: Option<SharedOpDesc>, op_dir: &OpDir,
r: Ref)
{
let spec = fetch_atom_op_spec(name.clone(), spec, op_dir);
let f_a = if name.as_str() == "." && arity == 2 {
Addr::Lis(self.heap.h)
} else {
let h = self.heap.h;
self.heap.push(HeapCellValue::NamedStr(arity as usize, name, spec));
Addr::Str(h)
};
for _ in 0 .. arity {
let h = self.heap.h;
self.heap.push(HeapCellValue::Addr(Addr::HeapCell(h)));
}
self.bind(r, f_a);
}
pub(super) fn try_functor(&mut self, indices: &IndexStore) -> CallResult {
let stub = MachineError::functor_stub(clause_name!("functor"), 3);
let a1 = self.store(self.deref(self[temp_v!(1)].clone()));
@@ -2061,13 +2084,13 @@ impl MachineState {
Addr::Str(o) =>
match self.heap[o].clone() {
HeapCellValue::NamedStr(arity, name, spec) => {
let spec = fetch_op_spec(name.clone(), arity, spec, op_dir);
let spec = fetch_op_spec(name.clone(), arity, spec, &indices.op_dir);
self.try_functor_compound_case(name, arity, spec)
},
},
_ => self.fail = true
},
Addr::Lis(_) => {
let shared_op_desc = fetch_op_spec(clause_name!("."), 2, None, op_dir);
let shared_op_desc = fetch_op_spec(clause_name!("."), 2, None, &indices.op_dir);
self.try_functor_compound_case(clause_name!("."), 2, shared_op_desc)
},
Addr::AttrVar(..) | Addr::HeapCell(_) | Addr::StackCell(..) => {
@@ -2101,23 +2124,13 @@ impl MachineState {
match name {
Addr::Con(_) if arity == 0 =>
self.unify(a1, name),
Addr::Con(Constant::Atom(name, spec)) => {
let spec = fetch_atom_op_spec(name.clone(), spec, op_dir);
let f_a = if name.as_str() == "." && arity == 2 {
Addr::Lis(self.heap.h)
} else {
let h = self.heap.h;
self.heap.push(HeapCellValue::NamedStr(arity as usize, name, spec));
Addr::Str(h)
};
for _ in 0 .. arity {
let h = self.heap.h;
self.heap.push(HeapCellValue::Addr(Addr::HeapCell(h)));
}
self.unify(a1, f_a);
Addr::Con(Constant::Atom(name, spec)) =>
self.try_functor_fabricate_struct(name, arity, spec, &indices.op_dir,
a1.as_var().unwrap()),
Addr::Con(Constant::Char(c)) => {
let name = clause_name!(c.to_string(), indices.atom_tbl);
self.try_functor_fabricate_struct(name, arity, None, &indices.op_dir,
a1.as_var().unwrap());
},
Addr::Con(_) =>
return Err(self.error_form(MachineError::type_error(ValidType::Atom, name),
@@ -2621,7 +2634,7 @@ impl MachineState {
pub(super)
fn sink_to_snapshot(&mut self) -> MachineState {
let mut snapshot = MachineState::with_capacity(0);
snapshot.hb = self.hb;
snapshot.e = self.e;
snapshot.b = self.b;
@@ -2634,7 +2647,7 @@ impl MachineState {
snapshot.fail = self.fail;
snapshot.trail = mem::replace(&mut self.trail, vec![]);
snapshot.pstr_trail = mem::replace(&mut self.pstr_trail, vec![]);
snapshot.heap = self.heap.take();
snapshot.heap = self.heap.take();
snapshot.mode = self.mode;
snapshot.and_stack = self.and_stack.take();
snapshot.or_stack = self.or_stack.take();

View File

@@ -323,7 +323,7 @@ impl MachineState {
Err(err)
}
}
pub(super) fn system_call(&mut self,
ct: &SystemClauseType,
indices: &mut IndexStore,
@@ -573,13 +573,17 @@ impl MachineState {
match result {
Some(Ok(b)) => self.unify(Addr::Con(Constant::Char(b as char)), a1),
_ => {
Some(Err(_)) => {
let end_of_file = clause_name!("end_of_file");
self.unify(a1, Addr::Con(Constant::Atom(end_of_file, None)));
},
None => {
let stub = MachineError::functor_stub(clause_name!("get_char"), 1);
let err = MachineError::representation_error(RepFlag::Character);
let err = self.error_form(err, stub);
return Err(err);
}
},
}
},
&SystemClauseType::GetModuleClause => {