summaryrefslogtreecommitdiff
path: root/yjit
diff options
context:
space:
mode:
authorTakashi Kokubun <takashikkbn@gmail.com>2023-09-12 10:52:40 -0700
committerGitHub <noreply@github.com>2023-09-12 13:52:40 -0400
commit0ae7f2d1ac354cd92d513f934aede0cabd6dbc9f (patch)
treeab7fd3603a6fa7d6ec727504c96aa4703d4d3797 /yjit
parenta98209b8a70345714ac5f3028e0591f3ee50bba7 (diff)
YJIT: Add compilation time counter (#8417)
* YJIT: Add compilation time counter * YJIT: Use Instant instead
Notes
Notes: Merged-By: maximecb <maximecb@ruby-lang.org>
Diffstat (limited to 'yjit')
-rw-r--r--yjit/src/core.rs4
-rw-r--r--yjit/src/stats.rs16
-rw-r--r--yjit/src/yjit.rs3
3 files changed, 20 insertions, 3 deletions
diff --git a/yjit/src/core.rs b/yjit/src/core.rs
index 805b7dd685..57b742724b 100644
--- a/yjit/src/core.rs
+++ b/yjit/src/core.rs
@@ -2248,7 +2248,7 @@ c_callable! {
/// See [gen_call_entry_stub_hit].
fn entry_stub_hit(entry_ptr: *const c_void, ec: EcPtr) -> *const u8 {
with_vm_lock(src_loc!(), || {
- match entry_stub_hit_body(entry_ptr, ec) {
+ match with_compile_time(|| { entry_stub_hit_body(entry_ptr, ec) }) {
Some(addr) => addr,
// Failed to service the stub by generating a new block so now we
// need to exit to the interpreter at the stubbed location.
@@ -2441,7 +2441,7 @@ c_callable! {
ec: EcPtr,
) -> *const u8 {
with_vm_lock(src_loc!(), || {
- branch_stub_hit_body(branch_ptr, target_idx, ec)
+ with_compile_time(|| { branch_stub_hit_body(branch_ptr, target_idx, ec) })
})
}
}
diff --git a/yjit/src/stats.rs b/yjit/src/stats.rs
index a4f95db6ae..30b60d9617 100644
--- a/yjit/src/stats.rs
+++ b/yjit/src/stats.rs
@@ -3,6 +3,8 @@
#![allow(dead_code)] // Counters are only used with the stats features
+use std::time::Instant;
+
use crate::codegen::CodegenGlobals;
use crate::core::Context;
use crate::core::for_each_iseq_payload;
@@ -411,6 +413,7 @@ make_counters! {
compiled_blockid_count,
compiled_block_count,
compiled_branch_count,
+ compile_time_ns,
compilation_failure,
block_next_count,
defer_count,
@@ -839,3 +842,16 @@ fn global_allocation_size() -> usize {
let stats = GLOBAL_ALLOCATOR.stats();
stats.bytes_allocated.saturating_sub(stats.bytes_deallocated)
}
+
+/// Measure the time taken by func() and add that to yjit_compile_time.
+pub fn with_compile_time<F, R>(func: F) -> R where F: FnOnce() -> R {
+ if get_option!(gen_stats) {
+ let start = Instant::now();
+ let ret = func();
+ let nanos = Instant::now().duration_since(start).as_nanos();
+ incr_counter_by!(compile_time_ns, nanos);
+ ret
+ } else {
+ func()
+ }
+}
diff --git a/yjit/src/yjit.rs b/yjit/src/yjit.rs
index 7f4cbbe18d..97799923d2 100644
--- a/yjit/src/yjit.rs
+++ b/yjit/src/yjit.rs
@@ -5,6 +5,7 @@ use crate::invariants::*;
use crate::options::*;
use crate::stats::YjitExitLocations;
use crate::stats::incr_counter;
+use crate::stats::with_compile_time;
use std::os::raw;
use std::sync::atomic::{AtomicBool, Ordering};
@@ -130,7 +131,7 @@ pub extern "C" fn rb_yjit_iseq_gen_entry_point(iseq: IseqPtr, ec: EcPtr, jit_exc
return std::ptr::null();
}
- let maybe_code_ptr = gen_entry_point(iseq, ec, jit_exception);
+ let maybe_code_ptr = with_compile_time(|| { gen_entry_point(iseq, ec, jit_exception) });
match maybe_code_ptr {
Some(ptr) => ptr.raw_ptr(),