flatten the instruction dispatch loop
This commit is contained in:
@@ -3,23 +3,26 @@ use indexmap::IndexMap;
|
||||
use crate::allocator::*;
|
||||
use crate::fixtures::*;
|
||||
use crate::forms::Level;
|
||||
use crate::instructions::*;
|
||||
use crate::machine::machine_indices::*;
|
||||
use crate::parser::ast::*;
|
||||
use crate::targets::CompilationTarget;
|
||||
|
||||
use crate::temp_v;
|
||||
|
||||
use fxhash::FxBuildHasher;
|
||||
|
||||
use std::cell::Cell;
|
||||
use std::collections::BTreeSet;
|
||||
use std::rc::Rc;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub(crate) struct DebrayAllocator {
|
||||
bindings: IndexMap<Rc<String>, VarData>,
|
||||
bindings: IndexMap<Rc<String>, VarData, FxBuildHasher>,
|
||||
arg_c: usize,
|
||||
temp_lb: usize,
|
||||
arity: usize, // 0 if not at head.
|
||||
contents: IndexMap<usize, Rc<String>>,
|
||||
contents: IndexMap<usize, Rc<String>, FxBuildHasher>,
|
||||
in_use: BTreeSet<usize>,
|
||||
}
|
||||
|
||||
@@ -123,7 +126,7 @@ impl DebrayAllocator {
|
||||
}
|
||||
}
|
||||
|
||||
fn evacuate_arg<'a, Target>(&mut self, chunk_num: usize, target: &mut Vec<Target>)
|
||||
fn evacuate_arg<'a, Target>(&mut self, chunk_num: usize, target: &mut Vec<Instruction>)
|
||||
where
|
||||
Target: CompilationTarget<'a>,
|
||||
{
|
||||
@@ -152,7 +155,7 @@ impl DebrayAllocator {
|
||||
var: &String,
|
||||
lvl: Level,
|
||||
term_loc: GenContext,
|
||||
target: &mut Vec<Target>,
|
||||
target: &mut Vec<Instruction>,
|
||||
) -> usize
|
||||
where
|
||||
Target: CompilationTarget<'a>,
|
||||
@@ -160,7 +163,7 @@ impl DebrayAllocator {
|
||||
match term_loc {
|
||||
GenContext::Head => {
|
||||
if let Level::Shallow = lvl {
|
||||
self.evacuate_arg(0, target);
|
||||
self.evacuate_arg::<Target>(0, target);
|
||||
self.alloc_with_cr(var)
|
||||
} else {
|
||||
self.alloc_with_ca(var)
|
||||
@@ -169,7 +172,7 @@ impl DebrayAllocator {
|
||||
GenContext::Mid(_) => self.alloc_with_ca(var),
|
||||
GenContext::Last(chunk_num) => {
|
||||
if let Level::Shallow = lvl {
|
||||
self.evacuate_arg(chunk_num, target);
|
||||
self.evacuate_arg::<Target>(chunk_num, target);
|
||||
self.alloc_with_cr(var)
|
||||
} else {
|
||||
self.alloc_with_ca(var)
|
||||
@@ -210,13 +213,18 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
arity: 0,
|
||||
arg_c: 1,
|
||||
temp_lb: 1,
|
||||
bindings: IndexMap::new(),
|
||||
contents: IndexMap::new(),
|
||||
bindings: IndexMap::with_hasher(FxBuildHasher::default()),
|
||||
contents: IndexMap::with_hasher(FxBuildHasher::default()),
|
||||
in_use: BTreeSet::new(),
|
||||
}
|
||||
}
|
||||
|
||||
fn mark_anon_var<Target>(&mut self, lvl: Level, term_loc: GenContext, target: &mut Vec<Target>)
|
||||
fn mark_anon_var<Target>(
|
||||
&mut self,
|
||||
lvl: Level,
|
||||
term_loc: GenContext,
|
||||
target: &mut Vec<Instruction>,
|
||||
)
|
||||
where
|
||||
Target: CompilationTarget<'a>,
|
||||
{
|
||||
@@ -228,7 +236,7 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
let k = self.arg_c;
|
||||
|
||||
if let GenContext::Last(chunk_num) = term_loc {
|
||||
self.evacuate_arg(chunk_num, target);
|
||||
self.evacuate_arg::<Target>(chunk_num, target);
|
||||
}
|
||||
|
||||
self.arg_c += 1;
|
||||
@@ -243,7 +251,7 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
lvl: Level,
|
||||
term_loc: GenContext,
|
||||
cell: &Cell<RegType>,
|
||||
target: &mut Vec<Target>,
|
||||
target: &mut Vec<Instruction>,
|
||||
) where
|
||||
Target: CompilationTarget<'a>,
|
||||
{
|
||||
@@ -254,7 +262,7 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
let k = self.arg_c;
|
||||
|
||||
if let GenContext::Last(chunk_num) = term_loc {
|
||||
self.evacuate_arg(chunk_num, target);
|
||||
self.evacuate_arg::<Target>(chunk_num, target);
|
||||
}
|
||||
|
||||
self.arg_c += 1;
|
||||
@@ -270,20 +278,18 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
cell.set(r);
|
||||
}
|
||||
|
||||
fn mark_var<Target>(
|
||||
fn mark_var<Target: CompilationTarget<'a>>(
|
||||
&mut self,
|
||||
var: Rc<String>,
|
||||
lvl: Level,
|
||||
cell: &'a Cell<VarReg>,
|
||||
term_loc: GenContext,
|
||||
target: &mut Vec<Target>,
|
||||
) where
|
||||
Target: CompilationTarget<'a>,
|
||||
{
|
||||
target: &mut Vec<Instruction>,
|
||||
) {
|
||||
let (r, is_new_var) = match self.get(var.clone()) {
|
||||
RegType::Temp(0) => {
|
||||
// here, r is temporary *and* unassigned.
|
||||
let o = self.alloc_reg_to_var(&var, lvl, term_loc, target);
|
||||
let o = self.alloc_reg_to_var::<Target>(&var, lvl, term_loc, target);
|
||||
cell.set(VarReg::Norm(RegType::Temp(o)));
|
||||
|
||||
(RegType::Temp(o), true)
|
||||
@@ -297,27 +303,25 @@ impl<'a> Allocator<'a> for DebrayAllocator {
|
||||
r => (r, false),
|
||||
};
|
||||
|
||||
self.mark_reserved_var(var, lvl, cell, term_loc, target, r, is_new_var);
|
||||
self.mark_reserved_var::<Target>(var, lvl, cell, term_loc, target, r, is_new_var);
|
||||
}
|
||||
|
||||
fn mark_reserved_var<Target>(
|
||||
fn mark_reserved_var<Target: CompilationTarget<'a>>(
|
||||
&mut self,
|
||||
var: Rc<String>,
|
||||
lvl: Level,
|
||||
cell: &'a Cell<VarReg>,
|
||||
term_loc: GenContext,
|
||||
target: &mut Vec<Target>,
|
||||
target: &mut Vec<Instruction>,
|
||||
r: RegType,
|
||||
is_new_var: bool,
|
||||
) where
|
||||
Target: CompilationTarget<'a>,
|
||||
{
|
||||
) {
|
||||
match lvl {
|
||||
Level::Root | Level::Shallow => {
|
||||
let k = self.arg_c;
|
||||
|
||||
if self.is_curr_arg_distinct_from(&var) {
|
||||
self.evacuate_arg(term_loc.chunk_num(), target);
|
||||
self.evacuate_arg::<Target>(term_loc.chunk_num(), target);
|
||||
}
|
||||
|
||||
self.arg_c += 1;
|
||||
|
||||
Reference in New Issue
Block a user