Don't attempt to wake up follower agents behind agents deleted during

live map edits, when the followers will also be deleted soon. Previously
this was crashing. #312

traffic_seitan once again makes it through the full montlake scenario,
and crashes on lakeslice around 3am.
This commit is contained in:
Dustin Carlino 2021-01-19 16:56:25 -08:00
parent 743b74510d
commit bccf389058
2 changed files with 19 additions and 9 deletions

View File

@ -671,7 +671,7 @@ impl DrivingSimState {
Traversable::Lane(l) => ctx.map.get_l(l).src_i,
Traversable::Turn(t) => t.parent,
};
if !ctx.handling_live_edits {
if ctx.handling_live_edits.is_none() {
ctx.intersections
.space_freed(now, i, ctx.scheduler, ctx.map);
}
@ -689,6 +689,14 @@ impl DrivingSimState {
// Update the follower so that they don't suddenly jump forwards.
if idx != dists.len() - 1 {
let (follower_id, follower_dist) = dists[idx + 1];
// If we're going to delete the follower soon, don't bother waking them up.
if let Some(ref deleting_agents) = ctx.handling_live_edits {
if deleting_agents.contains(&AgentID::Car(follower_id)) {
return;
}
}
let mut follower = self.cars.get_mut(&follower_id).unwrap();
// TODO If the leader vanished at a border node, this still jumps a bit -- the lead
// car's back is still sticking out. Need to still be bound by them, even though they
@ -803,12 +811,12 @@ impl DrivingSimState {
t,
ctx.scheduler,
ctx.map,
ctx.handling_live_edits,
ctx.handling_live_edits.is_some(),
);
}
Traversable::Lane(l) => {
old_queue.free_reserved_space(car);
if !ctx.handling_live_edits {
if ctx.handling_live_edits.is_none() {
ctx.intersections.space_freed(
now,
ctx.map.get_l(l).src_i,
@ -833,7 +841,7 @@ impl DrivingSimState {
// gets out of the way. So immediately promote them to
// WaitingToAdvance.
follower.state = CarState::WaitingToAdvance { blocked_since };
if self.recalc_lanechanging && !ctx.handling_live_edits {
if self.recalc_lanechanging && ctx.handling_live_edits.is_none() {
follower.router.opportunistically_lanechange(
&self.queues,
ctx.map,

View File

@ -70,8 +70,9 @@ pub(crate) struct Ctx<'a> {
pub cap: &'a mut CapSimState,
pub scheduler: &'a mut Scheduler,
pub map: &'a Map,
/// If true, live map edits are being processed. Some regular work should maybe be skipped.
pub handling_live_edits: bool,
/// If present, live map edits are being processed, and the agents specified are in the process
/// of being deleted. Some regular work should maybe be skipped.
pub handling_live_edits: Option<BTreeSet<AgentID>>,
}
/// Options controlling the traffic simulation.
@ -432,7 +433,7 @@ impl Sim {
cap: &mut self.cap,
scheduler: &mut self.scheduler,
map,
handling_live_edits: false,
handling_live_edits: None,
};
match cmd {
@ -837,6 +838,7 @@ impl Sim {
let (affected, num_parked_cars) = self.find_trips_affected_by_live_edits(map);
let num_trips_cancelled = affected.len();
let affected_agents: BTreeSet<AgentID> = affected.iter().map(|(a, _)| *a).collect();
// V1: Just cancel every trip crossing an affected area.
// (V2 is probably rerouting everyone, only cancelling when that fails)
@ -847,7 +849,7 @@ impl Sim {
cap: &mut self.cap,
scheduler: &mut self.scheduler,
map,
handling_live_edits: true,
handling_live_edits: Some(affected_agents),
};
for (agent, trip) in affected {
match agent {
@ -962,7 +964,7 @@ impl Sim {
cap: &mut self.cap,
scheduler: &mut self.scheduler,
map,
handling_live_edits: false,
handling_live_edits: None,
};
let vehicle = self.driving.delete_car(id, self.time, &mut ctx);
self.trips.cancel_trip(