From: Mark Thom Date: Thu, 8 Mar 2018 19:38:38 +0000 (-0700) Subject: further allocation fixes. X-Git-Tag: v0.8.110~533 X-Git-Url: https://git.sagredo.dev/?a=commitdiff_plain;h=cb9aafbccff7b9287e2bdf22b6a9311b1c73286e;p=scryer-prolog.git further allocation fixes. --- diff --git a/src/prolog/codegen.rs b/src/prolog/codegen.rs index 6cae3266..15299eda 100644 --- a/src/prolog/codegen.rs +++ b/src/prolog/codegen.rs @@ -542,7 +542,6 @@ impl<'a, TermMarker: Allocator<'a>> CodeGenerator let &Rule { head: (_, ref args, ref p1), ref clauses } = rule; let mut code = Vec::new(); - self.marker.reset_arg(args.len()); self.marker.reset_at_head(args); self.compile_seq_prelude(&conjunct_info, &mut code); @@ -613,7 +612,6 @@ impl<'a, TermMarker: Allocator<'a>> CodeGenerator let mut code = Vec::new(); if let &Term::Clause(_, _, ref args, _) = term { - self.marker.reset_arg(args.len()); self.marker.reset_at_head(args); let iter = FactInstruction::iter(term); diff --git a/src/prolog/debray_allocator.rs b/src/prolog/debray_allocator.rs index 47c48d9c..92b475a0 100644 --- a/src/prolog/debray_allocator.rs +++ b/src/prolog/debray_allocator.rs @@ -10,6 +10,7 @@ pub struct DebrayAllocator { bindings: HashMap, VarData>, arg_c: usize, temp_lb: usize, + arity: usize, // 0 if not at head. contents: HashMap>, in_use: BTreeSet, } @@ -31,12 +32,17 @@ impl DebrayAllocator { } } + fn is_in_use(&self, r: usize) -> bool { + let in_use_range = r < self.arity && r > self.arg_c; + self.in_use.contains(&r) || in_use_range + } + fn alloc_with_cr(&self, var: &Var) -> usize { match self.bindings.get(var) { Some(&VarData::Temp(_, _, ref tvd)) => { for &(_, reg) in tvd.use_set.iter() { - if !self.in_use.contains(®) { + if !self.is_in_use(reg) { return reg; } } @@ -44,7 +50,7 @@ impl DebrayAllocator { let mut result = 0; for reg in self.temp_lb .. { - if !self.in_use.contains(®) { + if !self.is_in_use(reg) { if !tvd.no_use_set.contains(®) { result = reg; break; @@ -63,7 +69,7 @@ impl DebrayAllocator { match self.bindings.get(var) { Some(&VarData::Temp(_, _, ref tvd)) => { for &(_, reg) in tvd.use_set.iter() { - if !self.in_use.contains(®) { + if !self.is_in_use(reg) { return reg; } } @@ -71,7 +77,7 @@ impl DebrayAllocator { let mut result = 0; for reg in self.temp_lb .. { - if !self.in_use.contains(®) { + if !self.is_in_use(reg) { if !tvd.no_use_set.contains(®) { if !tvd.conflict_set.contains(®) { result = reg; @@ -124,10 +130,10 @@ impl DebrayAllocator { let r = RegType::Temp(r); target.push(Target::move_to_register(r, k)); - + self.contents.remove(&k); self.contents.insert(r.reg_num(), var.clone()); - + self.record_register(var, r); self.in_use.insert(r.reg_num()); } @@ -193,6 +199,7 @@ impl<'a> Allocator<'a> for DebrayAllocator { fn new() -> DebrayAllocator { DebrayAllocator { + arity: 0, arg_c: 1, temp_lb: 1, bindings: HashMap::new(), @@ -335,16 +342,25 @@ impl<'a> Allocator<'a> for DebrayAllocator } fn reset_at_head(&mut self, args: &Vec>) { + self.reset_arg(args.len()); + self.arity = args.len(); + for (idx, arg) in args.iter().enumerate() { if let &Term::Var(_, ref var) = arg.as_ref() { - self.contents.insert(idx + 1, var.clone()); - self.in_use.insert(idx + 1); + let r = self.get(var.clone()); + + if !r.is_perm() && r.reg_num() == 0 { + self.in_use.insert(idx + 1); + self.contents.insert(idx + 1, var.clone()); + self.record_register(var.clone(), temp_v!(idx + 1)); + } } } } - + fn reset_arg(&mut self, arity: usize) { + self.arity = 0; self.arg_c = 1; - self.temp_lb = arity + 1; + self.temp_lb = arity + 1; } } diff --git a/src/prolog/io.rs b/src/prolog/io.rs index 70f7be5a..4a6e2497 100644 --- a/src/prolog/io.rs +++ b/src/prolog/io.rs @@ -601,7 +601,7 @@ pub fn compile_listing(wam: &mut Machine, src_str: &str) -> EvalSession let mut worker = TopLevelWorker::new(src_str.as_bytes(), wam.atom_tbl()); - + let tls = try_eval_session!(worker.parse_batch(&mut op_dir)); for tl in tls {