@@ -13,6 +13,7 @@ use std::cmp;
13
13
use tempfile:: TempDir ;
14
14
15
15
use collector:: { Benchmark as CollectedBenchmark , BenchmarkState , Patch , Run , Stat } ;
16
+ use collector:: self_profile:: SelfProfile ;
16
17
17
18
use failure:: { err_msg, Error , ResultExt } ;
18
19
use serde_json;
@@ -211,6 +212,8 @@ impl<'a> CargoProcess<'a> {
211
212
cmd. arg ( "-Zborrowck=mir" ) ;
212
213
cmd. arg ( "-Ztwo-phase-borrows" ) ;
213
214
}
215
+ cmd. arg ( "-Zself-profile" ) ;
216
+ cmd. arg ( "-Zprofile-json" ) ;
214
217
// --wrap-rustc-with is not a valid rustc flag. But rustc-fake
215
218
// recognizes it, strips it (and its argument) out, and uses it as an
216
219
// indicator that the rustc invocation should be profiled. This works
@@ -228,6 +231,7 @@ impl<'a> CargoProcess<'a> {
228
231
touch_all ( & self . cwd ) ?;
229
232
230
233
let output = command_output ( & mut cmd) ?;
234
+ let self_profile_json = fs:: read_to_string ( self . cwd . join ( "self_profile_results.json" ) ) ?;
231
235
if let Some ( ( ref mut processor, name, run_kind, run_kind_str, patch) ) =
232
236
self . processor_etc {
233
237
let data = ProcessOutputData {
@@ -237,6 +241,7 @@ impl<'a> CargoProcess<'a> {
237
241
run_kind,
238
242
run_kind_str,
239
243
patch,
244
+ self_profile : serde_json:: from_str ( & self_profile_json) . unwrap ( ) ,
240
245
} ;
241
246
match processor. process_output ( & data, output) {
242
247
Ok ( Retry :: No ) => return Ok ( ( ) ) ,
@@ -271,6 +276,7 @@ pub struct ProcessOutputData<'a> {
271
276
build_kind : BuildKind ,
272
277
run_kind : RunKind ,
273
278
run_kind_str : & ' a str ,
279
+ self_profile : SelfProfile ,
274
280
patch : Option < & ' a Patch > ,
275
281
}
276
282
@@ -290,11 +296,11 @@ pub trait Processor {
290
296
}
291
297
292
298
pub struct MeasureProcessor {
293
- clean_stats : Vec < Vec < Stat > > ,
294
- nll_stats : Vec < Vec < Stat > > ,
295
- base_incr_stats : Vec < Vec < Stat > > ,
296
- clean_incr_stats : Vec < Vec < Stat > > ,
297
- patched_incr_stats : Vec < ( Patch , Vec < Vec < Stat > > ) > ,
299
+ clean_stats : Vec < ( Vec < Stat > , SelfProfile ) > ,
300
+ nll_stats : Vec < ( Vec < Stat > , SelfProfile ) > ,
301
+ base_incr_stats : Vec < ( Vec < Stat > , SelfProfile ) > ,
302
+ clean_incr_stats : Vec < ( Vec < Stat > , SelfProfile ) > ,
303
+ patched_incr_stats : Vec < ( Patch , Vec < ( Vec < Stat > , SelfProfile ) > ) > ,
298
304
299
305
pub collected : CollectedBenchmark ,
300
306
}
@@ -329,20 +335,21 @@ impl Processor for MeasureProcessor {
329
335
-> Result < Retry , Error > {
330
336
match process_perf_stat_output ( output) {
331
337
Ok ( stats) => {
338
+ let self_profile = data. self_profile . clone ( ) ;
332
339
match data. run_kind {
333
- RunKind :: Clean => { self . clean_stats . push ( stats) ; }
334
- RunKind :: Nll => { self . nll_stats . push ( stats) ; }
335
- RunKind :: BaseIncr => { self . base_incr_stats . push ( stats) ; }
336
- RunKind :: CleanIncr => { self . clean_incr_stats . push ( stats) ; }
340
+ RunKind :: Clean => { self . clean_stats . push ( ( stats, self_profile ) ) ; }
341
+ RunKind :: Nll => { self . nll_stats . push ( ( stats, self_profile ) ) ; }
342
+ RunKind :: BaseIncr => { self . base_incr_stats . push ( ( stats, self_profile ) ) ; }
343
+ RunKind :: CleanIncr => { self . clean_incr_stats . push ( ( stats, self_profile ) ) ; }
337
344
RunKind :: PatchedIncrs => {
338
345
let patch = data. patch . unwrap ( ) ;
339
346
if let Some ( mut entry) =
340
347
self . patched_incr_stats . iter_mut ( ) . find ( |s| & s. 0 == patch)
341
348
{
342
- entry. 1 . push ( stats) ;
349
+ entry. 1 . push ( ( stats, self_profile ) ) ;
343
350
return Ok ( Retry :: No ) ;
344
351
}
345
- self . patched_incr_stats . push ( ( patch. clone ( ) , vec ! [ stats] ) ) ;
352
+ self . patched_incr_stats . push ( ( patch. clone ( ) , vec ! [ ( stats, self_profile ) ] ) ) ;
346
353
}
347
354
}
348
355
Ok ( Retry :: No )
@@ -776,10 +783,14 @@ fn process_perf_stat_output(output: process::Output) -> Result<Vec<Stat>, Deseri
776
783
Ok ( stats)
777
784
}
778
785
779
- fn process_stats ( build_kind : BuildKind , state : BenchmarkState , runs : & [ Vec < Stat > ] ) -> Run {
786
+ fn process_stats (
787
+ build_kind : BuildKind ,
788
+ state : BenchmarkState ,
789
+ runs : & [ ( Vec < Stat > , SelfProfile ) ] ,
790
+ ) -> Run {
780
791
let mut stats: HashMap < String , Vec < f64 > > = HashMap :: new ( ) ;
781
- for run in runs. clone ( ) {
782
- for stat in run {
792
+ for ( run_stats , _ ) in runs. clone ( ) {
793
+ for stat in run_stats {
783
794
stats
784
795
. entry ( stat. name . clone ( ) )
785
796
. or_insert_with ( || Vec :: new ( ) )
@@ -811,5 +822,7 @@ fn process_stats(build_kind: BuildKind, state: BenchmarkState, runs: &[Vec<Stat>
811
822
check : build_kind == BuildKind :: Check ,
812
823
release : build_kind == BuildKind :: Opt ,
813
824
state : state,
825
+ // TODO: Aggregate self profiles.
826
+ self_profile : runs[ 0 ] . 1 . clone ( ) ,
814
827
}
815
828
}
0 commit comments