Permalink
Browse files

[compiler][IR] Clean IR before extraction into a branch.

  • Loading branch information...
ptal committed Sep 22, 2018
1 parent dec96f5 commit 54a7d8db971ad27f8733b8795a7df64593dbdfd2
@@ -25,7 +25,6 @@ use middle;
use back;
use context::Context;
use ast::{JModule, JCrate, TestAnnotation};
use middle::ir::guarded_command::IR;
static ABORT_MSG: &'static str = "stop due to compilation errors";
@@ -36,7 +35,7 @@ pub fn run() {
.expect(ABORT_MSG);
}
pub fn front_mid_run<'a>(session: Session) -> Env<(Context, IR)> {
pub fn front_mid_run<'a>(session: Session) -> Env<Context> {
let env = run_front(session)
.map(|jcrate| Context::new(jcrate))
.ensure(ABORT_MSG);
@@ -64,11 +63,11 @@ fn run_front_module(env: Env<JCrate>, file: ModuleFile) -> Env<JCrate> {
})
}
fn run_middle<'a>(env: Env<Context>) -> Env<(Context, IR)> {
fn run_middle<'a>(env: Env<Context>) -> Env<Context> {
middle::analyse_bonsai(env)
}
pub fn run_back(session: Session, (context, _ir): (Context, IR)) -> Env<Context> {
pub fn run_back(session: Session, context: Context) -> Env<Context> {
assert_eq!(session.has_errors(), false);
context.ast.modules.clone()
.into_iter()
@@ -27,15 +27,14 @@ use middle::causality::solver::*;
use middle::causality::causal_stmt::*;
use middle::causality::symbolic_execution::*;
use middle::causality::model_parameters::*;
use middle::ir::compiler::AllInstants;
pub fn causality_analysis(session: Session, context: Context) -> Env<(Context, AllInstants)> {
pub fn causality_analysis(session: Session, context: Context) -> Env<Context> {
Env::value(session, context)
.and_then(index_ops_and_delay)
.and_then(execute_symbolically)
}
fn execute_symbolically(session: Session, (context, params): (Context, ModelParameters)) -> Env<(Context, AllInstants)> {
fn execute_symbolically(session: Session, (context, params): (Context, ModelParameters)) -> Env<Context> {
SymbolicExecution::for_each_instant(session, context, |env| {
env.and_then(|session, (context, stmt)|
build_causal_model(session, context, stmt, params.clone()))
@@ -15,11 +15,10 @@
use session::*;
use context::*;
use middle::causality::causal_model::*;
use middle::ir::scheduling::*;
use pcp::search::*;
use pcp::kernel::*;
pub fn solve_causal_model(session: Session, c: (Context, Vec<CausalModel>)) -> Env<(Context, Vec<Scheduling>)> {
pub fn solve_causal_model(session: Session, c: (Context, Vec<CausalModel>)) -> Env<Context> {
let solver = Solver::new(session, c.0, c.1);
solver.solve_all()
}
@@ -35,26 +34,24 @@ impl Solver {
Solver { session, context, models }
}
pub fn solve_all(mut self) -> Env<(Context, Vec<Scheduling>)> {
pub fn solve_all(mut self) -> Env<Context> {
debug!("{} causal models\n", self.models.len());
debug!("{} instantaneous causal models\n", self.models.iter().filter(|m| m.instantaneous).count());
let mut schedule_paths = vec![];
for model in self.models.clone() {
if let Some(model) = self.prepare_model(model) {
match self.solve_model(model) {
Some(schedule) => schedule_paths.push(schedule),
None => break,
if !self.solve_model(model) {
break
}
}
}
if self.session.has_errors() {
Env::fake(self.session, (self.context, schedule_paths))
Env::fake(self.session, self.context)
} else {
Env::value(self.session, (self.context, schedule_paths))
Env::value(self.session, self.context)
}
}
fn solve_model(&mut self, model: CausalModel) -> Option<Scheduling> {
fn solve_model(&mut self, model: CausalModel) -> bool {
// Search step.
let space = model.clone().space;
let mut search = one_solution_engine();
@@ -66,12 +63,12 @@ impl Solver {
match status {
Status::Satisfiable => {
trace!("{:?}\n\n{:?}", space.vstore, space.cstore);
Some(Scheduling::new(model, space))
true
},
Status::Unsatisfiable => {
self.err_unsatisfiable_model();
trace!("{:?}\n\n{:?}", space.vstore, space.cstore);
None
false
}
Status::EndOfSearch
| Status::Unknown(_) => unreachable!(
@@ -17,11 +17,9 @@
use context::*;
use session::*;
use middle::causality::causal_model::CausalModel;
use middle::ir::compiler::{Instant, AllInstants};
use middle::ir::scheduling::*;
use gcollections::VectorStack;
use gcollections::ops::*;
use std::collections::{HashSet, HashMap};
use std::collections::{HashSet};
/// A state is the set of all delay statements that must be resumed in the next instant.
/// Therefore, `usize` are only pushed by parallel statements.
@@ -125,6 +123,20 @@ impl StatesSet {
}
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct Instant {
pub locations: State,
pub program: Stmt
}
impl Instant
{
pub fn new(locations: State, program: Stmt) -> Self {
Instant { locations, program }
}
}
#[derive(Clone, Debug, PartialEq, Eq)]
enum ResidualStmt {
Terminated,
@@ -136,8 +148,7 @@ pub struct SymbolicExecution {
session: Session,
context: Context,
visited_states: Vec<State>,
next_instants: VectorStack<Instant>,
all_instants: Vec<Instant>,
next_instants: VectorStack<Instant>
}
impl SymbolicExecution
@@ -147,15 +158,13 @@ impl SymbolicExecution
session: session,
context: context,
visited_states: vec![],
next_instants: VectorStack::empty(),
all_instants: vec![]
next_instants: VectorStack::empty()
}
}
pub fn for_each_instant<F>(mut session: Session, mut context: Context, f: F) -> Env<(Context, AllInstants)>
where F: Clone + Fn(Env<(Context, Stmt)>) -> Env<(Context, Vec<Scheduling>)>
pub fn for_each_instant<F>(mut session: Session, mut context: Context, f: F) -> Env<Context>
where F: Clone + Fn(Env<(Context, Stmt)>) -> Env<Context>
{
let mut all_instants = HashMap::new();
let mut fake = false;
for uid in context.entry_points.clone() {
let mut this = SymbolicExecution::new(session, context);
@@ -164,17 +173,16 @@ impl SymbolicExecution
let (s, data) = env.decompose();
fake = fake || data.is_fake();
match data {
Partial::Value((c, instants))
| Partial::Fake((c, instants)) => {
all_instants.insert(uid, instants);
Partial::Value(c)
| Partial::Fake(c) => {
context = c;
session = s;
}
_ => { return Env::nothing(s) }
}
}
if fake { Env::fake(session, (context, all_instants)) }
else { Env::value(session, (context, all_instants))}
if fake { Env::fake(session, context) }
else { Env::value(session, context)}
}
fn push_process(&mut self, uid: ProcessUID) {
@@ -183,27 +191,25 @@ impl SymbolicExecution
self.push_instant(Some(process.body), state);
}
fn for_each<F>(mut self, f: F) -> Env<(Context, Vec<Instant>)>
where F: Fn(Env<(Context, Stmt)>) -> Env<(Context, Vec<Scheduling>)>
fn for_each<F>(mut self, f: F) -> Env<Context>
where F: Fn(Env<(Context, Stmt)>) -> Env<Context>
{
let mut fake = false;
while let Some(mut instant) = self.next() {
while let Some(instant) = self.next() {
let env = f(Env::value(self.session, (self.context, instant.program.clone())));
let (session, data) = env.decompose();
fake = fake || data.is_fake();
match data {
Partial::Value((context, path_schedules))
| Partial::Fake((context, path_schedules)) => {
instant.path_schedules = path_schedules;
self.all_instants.push(instant);
Partial::Value(context)
| Partial::Fake(context) => {
self.context = context;
self.session = session;
}
_ => { return Env::nothing(session) }
}
}
if fake { Env::fake(self.session, (self.context, self.all_instants)) }
else { Env::value(self.session, (self.context, self.all_instants))}
if fake { Env::fake(self.session, self.context) }
else { Env::value(self.session, self.context)}
}
/// Returns `true` if the state has not been visited before.
@@ -214,7 +220,7 @@ impl SymbolicExecution
fn push_instant(&mut self, next_program: Option<Stmt>, state: State) {
self.visited_states.push(state.clone());
let nothing = Stmt::new(DUMMY_SP, StmtKind::Nothing);
let instant = Instant::init(state, next_program.clone().unwrap_or(nothing));
let instant = Instant::new(state, next_program.clone().unwrap_or(nothing));
self.next_instants.push(instant);
}
Oops, something went wrong.

0 comments on commit 54a7d8d

Please sign in to comment.