mirror of
https://github.com/roc-lang/roc.git
synced 2025-10-01 07:41:12 +00:00
fix deadlock in file.rs
This commit is contained in:
parent
3aa6455795
commit
6490956a84
1 changed files with 194 additions and 196 deletions
|
@ -293,7 +293,7 @@ struct ModuleCache<'a> {
|
||||||
sources: MutMap<ModuleId, (PathBuf, &'a str)>,
|
sources: MutMap<ModuleId, (PathBuf, &'a str)>,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) -> BuildTask<'a> {
|
fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) -> Vec<BuildTask<'a>> {
|
||||||
// we blindly assume all dependencies are met
|
// we blindly assume all dependencies are met
|
||||||
|
|
||||||
match state.dependencies.status.get_mut(&(module_id, phase)) {
|
match state.dependencies.status.get_mut(&(module_id, phase)) {
|
||||||
|
@ -301,11 +301,20 @@ fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) ->
|
||||||
// start this phase!
|
// start this phase!
|
||||||
*current = Status::Pending;
|
*current = Status::Pending;
|
||||||
}
|
}
|
||||||
Some(Status::Pending) | Some(Status::Done) => {
|
Some(Status::Pending) => {
|
||||||
// don't start this task again!
|
// don't start this task again!
|
||||||
todo!();
|
return vec![];
|
||||||
|
}
|
||||||
|
Some(Status::Done) => {
|
||||||
|
// don't start this task again, but tell those waiting for it they can continue
|
||||||
|
return state
|
||||||
|
.dependencies
|
||||||
|
.notify(module_id, phase)
|
||||||
|
.into_iter()
|
||||||
|
.map(|(module_id, phase)| start_phase(module_id, phase, state))
|
||||||
|
.flatten()
|
||||||
|
.collect();
|
||||||
}
|
}
|
||||||
|
|
||||||
None => match phase {
|
None => match phase {
|
||||||
Phase::LoadHeader => {
|
Phase::LoadHeader => {
|
||||||
// this is fine, mark header loading as pending
|
// this is fine, mark header loading as pending
|
||||||
|
@ -321,6 +330,7 @@ fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) ->
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let task = {
|
||||||
match phase {
|
match phase {
|
||||||
Phase::LoadHeader => {
|
Phase::LoadHeader => {
|
||||||
let dep_name = state
|
let dep_name = state
|
||||||
|
@ -350,7 +360,8 @@ fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) ->
|
||||||
|
|
||||||
let deps_by_name = &parsed.deps_by_name;
|
let deps_by_name = &parsed.deps_by_name;
|
||||||
let num_deps = deps_by_name.len();
|
let num_deps = deps_by_name.len();
|
||||||
let mut dep_idents: MutMap<ModuleId, IdentIds> = IdentIds::exposed_builtins(num_deps);
|
let mut dep_idents: MutMap<ModuleId, IdentIds> =
|
||||||
|
IdentIds::exposed_builtins(num_deps);
|
||||||
|
|
||||||
let State {
|
let State {
|
||||||
ident_ids_by_module,
|
ident_ids_by_module,
|
||||||
|
@ -496,6 +507,9 @@ fn start_phase<'a>(module_id: ModuleId, phase: Phase, state: &mut State<'a>) ->
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
vec![task]
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
@ -1329,6 +1343,21 @@ where
|
||||||
.unwrap()
|
.unwrap()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn start_tasks<'a>(
|
||||||
|
work: MutSet<(ModuleId, Phase)>,
|
||||||
|
state: &mut State<'a>,
|
||||||
|
injector: &Injector<BuildTask<'a>>,
|
||||||
|
worker_listeners: &'a [Sender<WorkerMsg>],
|
||||||
|
) -> Result<(), LoadingProblem> {
|
||||||
|
for (module_id, phase) in work {
|
||||||
|
for task in start_phase(module_id, phase, state) {
|
||||||
|
enqueue_task(&injector, worker_listeners, task)?
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
fn update<'a>(
|
fn update<'a>(
|
||||||
mut state: State<'a>,
|
mut state: State<'a>,
|
||||||
msg: Msg<'a>,
|
msg: Msg<'a>,
|
||||||
|
@ -1384,19 +1413,11 @@ fn update<'a>(
|
||||||
|
|
||||||
state.module_cache.headers.insert(header.module_id, header);
|
state.module_cache.headers.insert(header.module_id, header);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
|
|
||||||
let work = state.dependencies.notify(home, Phase::LoadHeader);
|
let work = state.dependencies.notify(home, Phase::LoadHeader);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
}
|
}
|
||||||
|
@ -1412,11 +1433,7 @@ fn update<'a>(
|
||||||
|
|
||||||
let work = state.dependencies.notify(module_id, Phase::Parse);
|
let work = state.dependencies.notify(module_id, Phase::Parse);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
}
|
}
|
||||||
|
@ -1452,11 +1469,7 @@ fn update<'a>(
|
||||||
.dependencies
|
.dependencies
|
||||||
.notify(module_id, Phase::CanonicalizeAndConstrain);
|
.notify(module_id, Phase::CanonicalizeAndConstrain);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
}
|
}
|
||||||
|
@ -1503,11 +1516,7 @@ fn update<'a>(
|
||||||
.notify(module_id, Phase::CanonicalizeAndConstrain),
|
.notify(module_id, Phase::CanonicalizeAndConstrain),
|
||||||
);
|
);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
}
|
}
|
||||||
|
@ -1594,11 +1603,7 @@ fn update<'a>(
|
||||||
state.constrained_ident_ids.insert(module_id, ident_ids);
|
state.constrained_ident_ids.insert(module_id, ident_ids);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
|
@ -1646,11 +1651,8 @@ fn update<'a>(
|
||||||
.dependencies
|
.dependencies
|
||||||
.notify(module_id, Phase::FindSpecializations);
|
.notify(module_id, Phase::FindSpecializations);
|
||||||
|
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
}
|
}
|
||||||
MadeSpecializations {
|
MadeSpecializations {
|
||||||
|
@ -1718,11 +1720,7 @@ fn update<'a>(
|
||||||
// the originally requested module, we're all done!
|
// the originally requested module, we're all done!
|
||||||
return Ok(state);
|
return Ok(state);
|
||||||
} else {
|
} else {
|
||||||
for (module_id, phase) in work {
|
start_tasks(work, &mut state, &injector, worker_listeners)?;
|
||||||
let task = start_phase(module_id, phase, &mut state);
|
|
||||||
|
|
||||||
enqueue_task(&injector, worker_listeners, task)?
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(state)
|
Ok(state)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue