diff --git a/abstutil/src/lib.rs b/abstutil/src/lib.rs index 6c928786fd..08d0e178e4 100644 --- a/abstutil/src/lib.rs +++ b/abstutil/src/lib.rs @@ -21,6 +21,6 @@ pub use io::{ write_json, }; pub use logs::{format_log_record, LogAdapter}; -pub use time::{elapsed_seconds, Progress}; +pub use time::{elapsed_seconds, Timer}; const PROGRESS_FREQUENCY_SECONDS: f64 = 0.2; diff --git a/abstutil/src/time.rs b/abstutil/src/time.rs index 99ad1f874f..230b39db83 100644 --- a/abstutil/src/time.rs +++ b/abstutil/src/time.rs @@ -7,7 +7,7 @@ pub fn elapsed_seconds(since: Instant) -> f64 { (dt.as_secs() as f64) + (f64::from(dt.subsec_nanos()) * 1e-9) } -pub struct Progress { +struct Progress { label: String, processed_items: usize, total_items: usize, @@ -16,7 +16,7 @@ pub struct Progress { } impl Progress { - pub fn new(label: &str, total_items: usize) -> Progress { + fn new(label: &str, total_items: usize) -> Progress { Progress { label: label.to_string(), processed_items: 0, @@ -26,7 +26,8 @@ impl Progress { } } - pub fn next(&mut self) { + // Returns when done + fn next(&mut self, padding: String) -> Option { self.processed_items += 1; if self.processed_items > self.total_items { panic!( @@ -38,20 +39,116 @@ impl Progress { let done = self.processed_items == self.total_items; if elapsed_seconds(self.last_printed_at) >= PROGRESS_FREQUENCY_SECONDS || done { self.last_printed_at = Instant::now(); - // TODO blank till end of current line - print!( + let line = format!( "{}{}: {}/{}... {}s", - "\r", + padding, self.label, self.processed_items, self.total_items, - elapsed_seconds(self.started_at), + elapsed_seconds(self.started_at) ); + // TODO blank till end of current line + print!("\r{}", line); if done { println!(""); + return Some(line); } else { stdout().flush().unwrap(); } } + None + } +} + +enum StackEntry { + TimerSpan(TimerSpan), + Progress(Progress), +} + +// Hierarchial magic +pub struct Timer { + results: Vec, + stack: Vec, +} + +struct TimerSpan { + name: String, + started_at: Instant, +} + +impl Timer { + pub fn new() -> Timer { + Timer { + results: Vec::new(), + stack: Vec::new(), + } + } + + pub fn done(self) { + assert!(self.stack.is_empty()); + println!(""); + for line in self.results { + println!("{}", line); + } + println!(""); + } + + pub fn start(&mut self, name: &str) { + println!("{}- {}...", " ".repeat(self.stack.len()), name); + self.stack.push(StackEntry::TimerSpan(TimerSpan { + name: name.to_string(), + started_at: Instant::now(), + })); + } + + pub fn stop(&mut self, name: &str) { + let span = match self.stack.pop().unwrap() { + StackEntry::TimerSpan(s) => s, + StackEntry::Progress(p) => panic!( + "stop({}) while a Progress({}, {}/{}) is top of the stack", + name, p.label, p.processed_items, p.total_items + ), + }; + assert_eq!(span.name, name); + let line = format!( + "{}- {} took {}s", + " ".repeat(self.stack.len()), + name, + elapsed_seconds(span.started_at) + ); + println!("{}", line); + self.results.push(line); + } + + pub fn start_iter(&mut self, name: &str, total_items: usize) { + if total_items == 0 { + panic!("Can't start_iter({}, 0)", name); + } + if let Some(StackEntry::Progress(p)) = self.stack.last() { + panic!( + "Can't start_iter({}) while Progress({}) is top of the stack", + name, p.label + ); + } + + self.stack + .push(StackEntry::Progress(Progress::new(name, total_items))); + } + + pub fn next(&mut self) { + let padding = format!("{} - ", " ".repeat(self.stack.len() - 1)); + let done = if let Some(StackEntry::Progress(ref mut progress)) = self.stack.last_mut() { + if let Some(result) = progress.next(padding) { + self.results.push(result); + true + } else { + false + } + } else { + panic!("Can't next() while a TimerSpan is top of the stack"); + }; + if done { + self.stack.pop(); + } } } diff --git a/docs/backlog.md b/docs/backlog.md index 9d9bde3612..1c84607637 100644 --- a/docs/backlog.md +++ b/docs/backlog.md @@ -9,8 +9,6 @@ - run clippy everywhere - presubmit script - also enforce consistent style (import order, extern crate only in mod.rs or lib.rs, derive order, struct initialization order) -- profiling - - https://github.com/TyOverby/flame ## Conga line idea diff --git a/editor/Cargo.toml b/editor/Cargo.toml index dd3b536b1f..94695e6df0 100644 --- a/editor/Cargo.toml +++ b/editor/Cargo.toml @@ -12,7 +12,6 @@ cpuprofiler = "0.0.3" dimensioned = { git = "https://github.com/paholg/dimensioned", rev = "0e1076ebfa5128d1ee544bdc9754c948987b6fe3", features = ["serde"] } downcast = "0.9.2" ezgui = { path = "../ezgui" } -flame = "0.2.2" generator = "0.6" geo = "0.9.1" geom = { path = "../geom" } diff --git a/editor/src/main.rs b/editor/src/main.rs index f3fd23624f..f78e339c0f 100644 --- a/editor/src/main.rs +++ b/editor/src/main.rs @@ -9,7 +9,6 @@ extern crate dimensioned; #[macro_use] extern crate downcast; extern crate ezgui; -extern crate flame; #[macro_use] extern crate generator; extern crate geo; diff --git a/editor/src/plugins/neighborhood_summary.rs b/editor/src/plugins/neighborhood_summary.rs index 7b19bc1bc8..879458c387 100644 --- a/editor/src/plugins/neighborhood_summary.rs +++ b/editor/src/plugins/neighborhood_summary.rs @@ -15,13 +15,17 @@ pub struct NeighborhoodSummary { } impl NeighborhoodSummary { - pub fn new(map: &Map) -> NeighborhoodSummary { + pub fn new(map: &Map, timer: &mut abstutil::Timer) -> NeighborhoodSummary { + let neighborhoods = abstutil::load_all_objects("neighborhoods", map.get_name()); + timer.start_iter("precompute neighborhood members", neighborhoods.len()); NeighborhoodSummary { - regions: abstutil::load_all_objects("neighborhoods", map.get_name()) + regions: neighborhoods .into_iter() .enumerate() - .map(|(idx, (_, n))| Region::new(idx, n, map)) - .collect(), + .map(|(idx, (_, n))| { + timer.next(); + Region::new(idx, n, map) + }).collect(), active: false, last_summary: None, } diff --git a/editor/src/render/map.rs b/editor/src/render/map.rs index a751bcfbba..058b0e5ad8 100644 --- a/editor/src/render/map.rs +++ b/editor/src/render/map.rs @@ -1,8 +1,8 @@ // Copyright 2018 Google LLC, licensed under http://www.apache.org/licenses/LICENSE-2.0 -use abstutil::Progress; use aabb_quadtree::geom::{Point, Rect}; use aabb_quadtree::QuadTree; +use abstutil::Timer; use control::ControlMap; use geom::{Bounds, Pt2D}; use kml::{ExtraShape, ExtraShapeID}; @@ -43,11 +43,16 @@ pub struct DrawMap { } impl DrawMap { - pub fn new(map: &Map, control_map: &ControlMap, raw_extra_shapes: Vec) -> DrawMap { + pub fn new( + map: &Map, + control_map: &ControlMap, + raw_extra_shapes: Vec, + timer: &mut Timer, + ) -> DrawMap { let mut lanes: Vec = Vec::new(); - let mut progress = Progress::new("make DrawLanes", map.all_lanes().len()); + timer.start_iter("make DrawLanes", map.all_lanes().len()); for l in map.all_lanes() { - progress.next(); + timer.next(); lanes.push(DrawLane::new(l, map, control_map)); } @@ -89,6 +94,7 @@ impl DrawMap { let bounds = map.get_bounds(); let map_bbox = get_bbox(bounds); + timer.start("create quadtree"); let mut quadtree = QuadTree::default(map_bbox); // TODO use iter chain if everything was boxed as a renderable... for obj in &lanes { @@ -112,6 +118,7 @@ impl DrawMap { for obj in &areas { quadtree.insert_with_box(obj.get_id(), get_bbox(obj.get_bounds())); } + timer.stop("create quadtree"); DrawMap { lanes, diff --git a/editor/src/ui.rs b/editor/src/ui.rs index c817c229aa..bcb578c372 100644 --- a/editor/src/ui.rs +++ b/editor/src/ui.rs @@ -7,7 +7,6 @@ use colors::ColorScheme; use control::ControlMap; //use cpuprofiler; use ezgui::{Canvas, Color, EventLoopMode, GfxCtx, Text, UserInput, BOTTOM_LEFT, GUI}; -use flame; use kml; use map_model::{IntersectionID, Map}; use objects::{Ctx, ID, ROOT_MENU}; @@ -232,27 +231,27 @@ impl PluginsPerMap { impl PerMapUI { pub fn new(flags: SimFlags, kml: &Option) -> (PerMapUI, PluginsPerMap) { - flame::start("setup"); - let (map, control_map, sim) = sim::load(flags.clone(), Some(sim::Tick::from_seconds(30))); + let mut timer = abstutil::Timer::new(); + timer.start("PerMapUI setup"); + + let (map, control_map, sim) = + sim::load(flags.clone(), Some(sim::Tick::from_seconds(30)), &mut timer); let extra_shapes = if let Some(path) = kml { kml::load(&path, &map.get_gps_bounds()).expect("Couldn't load extra KML shapes") } else { Vec::new() }; - flame::start("draw_map"); - let draw_map = DrawMap::new(&map, &control_map, extra_shapes); - flame::end("draw_map"); + timer.start("draw_map"); + let draw_map = DrawMap::new(&map, &control_map, extra_shapes, &mut timer); + timer.stop("draw_map"); - flame::start("steepness_viz"); let steepness_viz = plugins::steep::SteepnessVisualizer::new(&map); - flame::end("steepness_viz"); - flame::start("neighborhood_summary"); - let neighborhood_summary = plugins::neighborhood_summary::NeighborhoodSummary::new(&map); - flame::end("neighborhood_summary"); + let neighborhood_summary = + plugins::neighborhood_summary::NeighborhoodSummary::new(&map, &mut timer); - flame::end("setup"); - flame::dump_stdout(); + timer.stop("PerMapUI setup"); + timer.done(); let state = PerMapUI { map, diff --git a/map_model/Cargo.toml b/map_model/Cargo.toml index 6946db4fc8..f2bc1d970b 100644 --- a/map_model/Cargo.toml +++ b/map_model/Cargo.toml @@ -7,7 +7,6 @@ authors = ["Dustin Carlino "] aabb-quadtree = "0.1.0" abstutil = { path = "../abstutil" } dimensioned = { git = "https://github.com/paholg/dimensioned", rev = "0e1076ebfa5128d1ee544bdc9754c948987b6fe3", features = ["serde"] } -flame = "0.2.2" geo = "0.9.1" geom = { path = "../geom" } gtfs = { path = "../gtfs" } diff --git a/map_model/src/lib.rs b/map_model/src/lib.rs index dd72e933e1..4cb8a09fe0 100644 --- a/map_model/src/lib.rs +++ b/map_model/src/lib.rs @@ -1,7 +1,6 @@ extern crate aabb_quadtree; extern crate abstutil; extern crate dimensioned; -extern crate flame; extern crate geo; extern crate geom; extern crate gtfs; diff --git a/map_model/src/make/buildings.rs b/map_model/src/make/buildings.rs index 52b50074f5..e03a23b09f 100644 --- a/map_model/src/make/buildings.rs +++ b/map_model/src/make/buildings.rs @@ -1,4 +1,4 @@ -use abstutil::Progress; +use abstutil::Timer; use dimensioned::si; use geom::{Bounds, HashablePt2D, Line, PolyLine, Pt2D}; use make::sidewalk_finder::find_sidewalk_points; @@ -12,13 +12,15 @@ pub fn make_all_buildings( gps_bounds: &Bounds, bounds: &Bounds, lanes: &Vec, + timer: &mut Timer, ) { + timer.start("convert buildings"); let mut pts_per_bldg: Vec> = Vec::new(); let mut center_per_bldg: Vec = Vec::new(); let mut query: HashSet = HashSet::new(); - let mut progress = Progress::new("get building center points", input.len()); + timer.start_iter("get building center points", input.len()); for b in input { - progress.next(); + timer.next(); let pts = b .points .iter() @@ -31,11 +33,11 @@ pub fn make_all_buildings( } // Skip buildings that're too far away from their sidewalk - let sidewalk_pts = find_sidewalk_points(bounds, query, lanes, 100.0 * si::M); + let sidewalk_pts = find_sidewalk_points(bounds, query, lanes, 100.0 * si::M, timer); - let mut progress = Progress::new("create building front paths", pts_per_bldg.len()); + timer.start_iter("create building front paths", pts_per_bldg.len()); for (idx, points) in pts_per_bldg.into_iter().enumerate() { - progress.next(); + timer.next(); let bldg_center = center_per_bldg[idx]; if let Some((sidewalk, dist_along)) = sidewalk_pts.get(&bldg_center) { let (sidewalk_pt, _) = lanes[sidewalk.0].dist_along(*dist_along); @@ -64,6 +66,7 @@ pub fn make_all_buildings( discarded ); } + timer.stop("convert buildings"); } // Adjust the path to start on the building's border, not center diff --git a/map_model/src/make/bus_stops.rs b/map_model/src/make/bus_stops.rs index 28aea97111..02a22b94b0 100644 --- a/map_model/src/make/bus_stops.rs +++ b/map_model/src/make/bus_stops.rs @@ -1,3 +1,4 @@ +use abstutil::Timer; use dimensioned::si; use geom::{Bounds, HashablePt2D, Pt2D}; use gtfs; @@ -14,7 +15,9 @@ pub fn make_bus_stops( bus_routes: &Vec, gps_bounds: &Bounds, bounds: &Bounds, + timer: &mut Timer, ) -> (BTreeMap, Vec) { + timer.start("make bus stops"); let mut bus_stop_pts: HashSet = HashSet::new(); let mut route_lookups: MultiMap = MultiMap::new(); for route in bus_routes { @@ -29,7 +32,7 @@ pub fn make_bus_stops( let mut stops_per_sidewalk: MultiMap, HashablePt2D)> = MultiMap::new(); for (pt, (lane, dist_along)) in - find_sidewalk_points(bounds, bus_stop_pts, lanes, 10.0 * si::M).iter() + find_sidewalk_points(bounds, bus_stop_pts, lanes, 10.0 * si::M, timer).iter() { stops_per_sidewalk.insert(*lane, (*dist_along, *pt)); } @@ -95,6 +98,7 @@ pub fn make_bus_stops( }); } } + timer.stop("make bus stops"); (bus_stops, routes) } diff --git a/map_model/src/make/parcels.rs b/map_model/src/make/parcels.rs index 0b56547b8a..17b8bf960a 100644 --- a/map_model/src/make/parcels.rs +++ b/map_model/src/make/parcels.rs @@ -1,3 +1,4 @@ +use abstutil::Timer; use dimensioned::si; use geom::{Bounds, HashablePt2D, Pt2D}; use make::sidewalk_finder::find_sidewalk_points; @@ -11,7 +12,9 @@ pub fn make_all_parcels( gps_bounds: &Bounds, bounds: &Bounds, lanes: &Vec, + timer: &mut Timer, ) { + timer.start("convert parcels"); let mut pts_per_parcel: Vec> = Vec::new(); let mut center_per_parcel: Vec = Vec::new(); let mut query: HashSet = HashSet::new(); @@ -28,7 +31,7 @@ pub fn make_all_parcels( } // Trim parcels that are too far away from the nearest sidewalk - let sidewalk_pts = find_sidewalk_points(bounds, query, lanes, 100.0 * si::M); + let sidewalk_pts = find_sidewalk_points(bounds, query, lanes, 100.0 * si::M, timer); for (idx, center) in center_per_parcel.into_iter().enumerate() { if sidewalk_pts.contains_key(¢er) { @@ -47,4 +50,5 @@ pub fn make_all_parcels( discarded ); } + timer.stop("convert parcels"); } diff --git a/map_model/src/make/sidewalk_finder.rs b/map_model/src/make/sidewalk_finder.rs index c0acb3efc5..778b46dc96 100644 --- a/map_model/src/make/sidewalk_finder.rs +++ b/map_model/src/make/sidewalk_finder.rs @@ -1,6 +1,6 @@ use aabb_quadtree::geom::{Point, Rect}; use aabb_quadtree::QuadTree; -use abstutil::Progress; +use abstutil::Timer; use dimensioned::si; use geo; use geo::prelude::{ClosestPoint, EuclideanDistance}; @@ -16,13 +16,18 @@ pub fn find_sidewalk_points( pts: HashSet, lanes: &Vec, max_dist_away: si::Meter, + timer: &mut Timer, ) -> HashMap)> { + if pts.is_empty() { + return HashMap::new(); + } + // Convert all sidewalks to LineStrings and index them with a quadtree. let mut lane_lines_quadtree: QuadTree = QuadTree::default(get_bbox(bounds)); let mut lane_lines: Vec<(LaneID, geo::LineString)> = Vec::new(); - let mut progress = Progress::new("lanes to LineStrings", lanes.len()); + timer.start_iter("lanes to LineStrings", lanes.len()); for l in lanes { - progress.next(); + timer.next(); if l.is_sidewalk() { lane_lines.push((l.id, lane_to_line_string(l))); lane_lines_quadtree.insert_with_box(lane_lines.len() - 1, lane_to_rect(l)); @@ -32,9 +37,9 @@ pub fn find_sidewalk_points( // For each point, find the closest point to any sidewalk, using the quadtree to prune the // search. let mut results: HashMap)> = HashMap::new(); - let mut progress = Progress::new("find closest sidewalk point", pts.len()); + timer.start_iter("find closest sidewalk point", pts.len()); for query_pt in pts { - progress.next(); + timer.next(); let query_geo_pt = geo::Point::new(query_pt.x(), query_pt.y()); let query_bbox = Rect { top_left: Point { diff --git a/map_model/src/map.rs b/map_model/src/map.rs index 7cc816c3cf..8aec3e5215 100644 --- a/map_model/src/map.rs +++ b/map_model/src/map.rs @@ -1,9 +1,8 @@ // Copyright 2018 Google LLC, licensed under http://www.apache.org/licenses/LICENSE-2.0 use abstutil; -use abstutil::{Error, Progress}; +use abstutil::{Error, Timer}; use edits::RoadEdits; -use flame; use geom::{Bounds, HashablePt2D, LonLat, PolyLine, Pt2D}; use make; use raw_data; @@ -35,13 +34,11 @@ pub struct Map { } impl Map { - pub fn new(path: &str, road_edits: RoadEdits) -> Result { - // TODO I think I want something a bit different than flame: - // - Print as each phase occurs - // - Print with nicely formatted durations - flame::start("read raw_data"); + pub fn new(path: &str, road_edits: RoadEdits, timer: &mut Timer) -> Result { + // TODO use read_binary's timer magic, not this + timer.start("read raw_data"); let data: raw_data::Map = abstutil::read_binary(path)?; - flame::end("read raw_data"); + timer.stop("read raw_data"); Ok(Map::create_from_raw( path::Path::new(path) .file_stem() @@ -51,10 +48,17 @@ impl Map { .unwrap(), data, road_edits, + timer, )) } - pub fn create_from_raw(name: String, data: raw_data::Map, road_edits: RoadEdits) -> Map { + pub fn create_from_raw( + name: String, + data: raw_data::Map, + road_edits: RoadEdits, + timer: &mut Timer, + ) -> Map { + timer.start("raw_map to Map"); let gps_bounds = data.get_gps_bounds(); let bounds = gps_to_map_bounds(&gps_bounds); let mut m = Map { @@ -90,7 +94,9 @@ impl Map { } let mut counter = 0; + timer.start_iter("expand roads to lanes", data.roads.len()); for (idx, r) in data.roads.iter().enumerate() { + timer.next(); let road_id = RoadID(idx); let road_center_pts = PolyLine::new( r.points @@ -158,9 +164,9 @@ impl Map { } } - let mut progress = Progress::new("trim lanes at each intersection", m.intersections.len()); + timer.start_iter("trim lanes at each intersection", m.intersections.len()); for i in &m.intersections { - progress.next(); + timer.next(); make::trim_lines(&mut m.lanes, i); if i.incoming_lanes.is_empty() && i.outgoing_lanes.is_empty() { panic!("{:?} is orphaned!", i); @@ -173,6 +179,7 @@ impl Map { &data.bus_routes, &gps_bounds, &bounds, + timer, ); m.bus_stops = stops; @@ -186,30 +193,26 @@ impl Map { m.intersections[t.parent.0].turns.push(t.id); } - { - let _guard = flame::start_guard(format!("make {} buildings", data.buildings.len())); - make::make_all_buildings( - &mut m.buildings, - &data.buildings, - &gps_bounds, - &bounds, - &m.lanes, - ); - for b in &m.buildings { - m.lanes[b.front_path.sidewalk.0].building_paths.push(b.id); - } + make::make_all_buildings( + &mut m.buildings, + &data.buildings, + &gps_bounds, + &bounds, + &m.lanes, + timer, + ); + for b in &m.buildings { + m.lanes[b.front_path.sidewalk.0].building_paths.push(b.id); } - { - let _guard = flame::start_guard(format!("make {} parcels", data.parcels.len())); - make::make_all_parcels( - &mut m.parcels, - &data.parcels, - &gps_bounds, - &bounds, - &m.lanes, - ); - } + make::make_all_parcels( + &mut m.parcels, + &data.parcels, + &gps_bounds, + &bounds, + &m.lanes, + timer, + ); for (idx, a) in data.areas.iter().enumerate() { m.areas.push(Area { @@ -225,11 +228,9 @@ impl Map { }); } - { - let _guard = flame::start_guard(format!("verify {} bus routes", routes.len())); - m.bus_routes = make::verify_bus_routes(&m, routes); - } + m.bus_routes = make::verify_bus_routes(&m, routes); + timer.stop("raw_map to Map"); m } diff --git a/sim/Cargo.toml b/sim/Cargo.toml index 49a0783bfb..497f7191ca 100644 --- a/sim/Cargo.toml +++ b/sim/Cargo.toml @@ -9,7 +9,6 @@ backtrace = "0.3.9" control = { path = "../control" } derivative = "1.0.0" dimensioned = { git = "https://github.com/paholg/dimensioned", rev = "0e1076ebfa5128d1ee544bdc9754c948987b6fe3", features = ["serde"] } -flame = "0.2.2" geom = { path = "../geom" } lazy_static = "1.1.0" log = "0.4.5" diff --git a/sim/src/helpers.rs b/sim/src/helpers.rs index 06864a793a..556990cf53 100644 --- a/sim/src/helpers.rs +++ b/sim/src/helpers.rs @@ -1,6 +1,5 @@ use abstutil; use control::ControlMap; -use flame; use map_model::{BuildingID, BusRoute, BusStopID, LaneID, Map, RoadID}; use std::collections::{BTreeSet, VecDeque}; use { @@ -40,14 +39,18 @@ impl SimFlags { } // Convenience method to setup everything. -pub fn load(flags: SimFlags, savestate_every: Option) -> (Map, ControlMap, Sim) { +pub fn load( + flags: SimFlags, + savestate_every: Option, + timer: &mut abstutil::Timer, +) -> (Map, ControlMap, Sim) { if flags.load.contains("data/save/") { assert_eq!(flags.edits_name, "no_edits"); info!("Resuming from {}", flags.load); - flame::start("read sim savestate"); + timer.start("read sim savestate"); let sim: Sim = abstutil::read_json(&flags.load).expect("loading sim state failed"); - flame::end("read sim savestate"); + timer.stop("read sim savestate"); let edits: MapEdits = abstutil::read_json(&format!( "../data/edits/{}/{}.json", @@ -60,7 +63,7 @@ pub fn load(flags: SimFlags, savestate_every: Option) -> (Map, ControlMap, sim.map_name, sim.edits_name )).unwrap_or_else(|_| { let map_path = format!("../data/raw_maps/{}.abst", sim.map_name); - Map::new(&map_path, edits.road_edits.clone()) + Map::new(&map_path, edits.road_edits.clone(), timer) .expect(&format!("Couldn't load map from {}", map_path)) }); let control_map = ControlMap::new(&map, edits.stop_signs, edits.traffic_signals); @@ -77,7 +80,7 @@ pub fn load(flags: SimFlags, savestate_every: Option) -> (Map, ControlMap, scenario.map_name, edits.edits_name )).unwrap_or_else(|_| { let map_path = format!("../data/raw_maps/{}.abst", scenario.map_name); - Map::new(&map_path, edits.road_edits.clone()) + Map::new(&map_path, edits.road_edits.clone(), timer) .expect(&format!("Couldn't load map from {}", map_path)) }); let control_map = ControlMap::new(&map, edits.stop_signs, edits.traffic_signals); @@ -99,19 +102,21 @@ pub fn load(flags: SimFlags, savestate_every: Option) -> (Map, ControlMap, .to_string(); info!("Loading map {}", flags.load); let edits = load_edits(&map_name, &flags); - let map = Map::new(&flags.load, edits.road_edits.clone()).expect("Couldn't load map"); + let map = + Map::new(&flags.load, edits.road_edits.clone(), timer).expect("Couldn't load map"); let control_map = ControlMap::new(&map, edits.stop_signs, edits.traffic_signals); - flame::start("create sim"); + timer.start("create sim"); let sim = Sim::new(&map, flags.run_name, flags.rng_seed, savestate_every); - flame::end("create sim"); + timer.stop("create sim"); (map, control_map, sim) } else if flags.load.contains("data/maps/") { assert_eq!(flags.edits_name, "no_edits"); info!("Loading map {}", flags.load); - flame::start("load binary map"); + // TODO dont do this + timer.start("load binary map"); let map: Map = abstutil::read_binary(&flags.load).expect("Couldn't load map"); - flame::end("load binary map"); + timer.stop("load binary map"); // TODO Bit sad to load edits to reconstitute ControlMap, but this is necessary right now let edits: MapEdits = abstutil::read_json(&format!( "../data/edits/{}/{}.json", @@ -119,9 +124,9 @@ pub fn load(flags: SimFlags, savestate_every: Option) -> (Map, ControlMap, map.get_road_edits().edits_name )).unwrap(); let control_map = ControlMap::new(&map, edits.stop_signs, edits.traffic_signals); - flame::start("create sim"); + timer.start("create sim"); let sim = Sim::new(&map, flags.run_name, flags.rng_seed, savestate_every); - flame::end("create sim"); + timer.stop("create sim"); (map, control_map, sim) } else { panic!("Don't know how to load {}", flags.load); diff --git a/sim/src/lib.rs b/sim/src/lib.rs index 22eb78f986..dbf90b790e 100644 --- a/sim/src/lib.rs +++ b/sim/src/lib.rs @@ -6,7 +6,6 @@ extern crate control; #[macro_use] extern crate derivative; extern crate dimensioned; -extern crate flame; extern crate geom; #[macro_use] extern crate lazy_static;