Skip to content

Commit

Permalink
[self-profiling] Include the estimated size of each cgu in the profile
Browse files Browse the repository at this point in the history
This is helpful when looking for CGUs where the size estimate isn't a
good indicator of compilation time.

I verified that moving the profiling timer call doesn't affect the
results.
  • Loading branch information
wesleywiser committed Nov 3, 2020
1 parent 338f939 commit efe703a
Show file tree
Hide file tree
Showing 2 changed files with 26 additions and 2 deletions.
6 changes: 4 additions & 2 deletions compiler/rustc_codegen_llvm/src/base.rs
Original file line number Diff line number Diff line change
Expand Up @@ -97,21 +97,23 @@ pub fn compile_codegen_unit(
tcx: TyCtxt<'tcx>,
cgu_name: Symbol,
) -> (ModuleCodegen<ModuleLlvm>, u64) {
let prof_timer = tcx.prof.generic_activity_with_arg("codegen_module", cgu_name.to_string());
let start_time = Instant::now();

let dep_node = tcx.codegen_unit(cgu_name).codegen_dep_node(tcx);
let (module, _) =
tcx.dep_graph.with_task(dep_node, tcx, cgu_name, module_codegen, dep_graph::hash_result);
let time_to_codegen = start_time.elapsed();
drop(prof_timer);

// We assume that the cost to run LLVM on a CGU is proportional to
// the time we needed for codegenning it.
let cost = time_to_codegen.as_nanos() as u64;

fn module_codegen(tcx: TyCtxt<'_>, cgu_name: Symbol) -> ModuleCodegen<ModuleLlvm> {
let cgu = tcx.codegen_unit(cgu_name);
let _prof_timer = tcx.prof.generic_activity_with_args(
"codegen_module",
&[cgu_name.to_string(), cgu.size_estimate().to_string()],
);
// Instantiate monomorphizations without filling out definitions yet...
let llvm_module = ModuleLlvm::new(tcx, &cgu_name.as_str());
{
Expand Down
22 changes: 22 additions & 0 deletions compiler/rustc_data_structures/src/profiling.rs
Original file line number Diff line number Diff line change
Expand Up @@ -272,6 +272,28 @@ impl SelfProfilerRef {
})
}

#[inline(always)]
pub fn generic_activity_with_args(
&self,
event_label: &'static str,
event_args: &[String],
) -> TimingGuard<'_> {
self.exec(EventFilter::GENERIC_ACTIVITIES, |profiler| {
let builder = EventIdBuilder::new(&profiler.profiler);
let event_label = profiler.get_or_alloc_cached_string(event_label);
let event_id = if profiler.event_filter_mask.contains(EventFilter::FUNCTION_ARGS) {
let event_args: Vec<_> = event_args
.iter()
.map(|s| profiler.get_or_alloc_cached_string(&s[..]))
.collect();
builder.from_label_and_args(event_label, &event_args)
} else {
builder.from_label(event_label)
};
TimingGuard::start(profiler, profiler.generic_activity_event_kind, event_id)
})
}

/// Start profiling a query provider. Profiling continues until the
/// TimingGuard returned from this call is dropped.
#[inline(always)]
Expand Down

0 comments on commit efe703a

Please sign in to comment.