From 1f517f6cea004eeb0fe56baa3114767fe7f59ba2 Mon Sep 17 00:00:00 2001 From: Jan-Erik Rediger Date: Mon, 5 Oct 2026 12:01:56 +0200 Subject: [PATCH 1/2] Profiler markers for rkv commits --- Cargo.lock | 7 +++++++ Makefile | 2 +- glean-core/Cargo.toml | 3 ++- glean-core/src/database/rkv.rs | 36 ++++++++++++++++++++++++++++++++++ supply-chain/config.toml | 4 ++++ 5 files changed, 50 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 4bc2f7122a..5060b78272 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -541,6 +541,12 @@ dependencies = [ "autocfg", ] +[[package]] +name = "gecko-profiler" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60f0e0112988282ef091969a75a3c181b505a7154a23d3a4f784da03a40a062b" + [[package]] name = "getrandom" version = "0.2.8" @@ -605,6 +611,7 @@ dependencies = [ "ctor", "env_logger", "flate2", + "gecko-profiler", "log", "malloc_size_of_derive", "mozbuild", diff --git a/Makefile b/Makefile index 65a1cef097..507f9fed88 100644 --- a/Makefile +++ b/Makefile @@ -95,7 +95,7 @@ test-python: build-python ## Run all Python tests lint: lint-rust lint-kotlin lint-swift lint-yaml lint-python lint-rust: ## Run cargo-clippy to lint Rust code - cargo clippy --all --all-targets --features "enable_env_logger gecko benchmark" -- -D warnings -A unknown-lints + cargo clippy --all --all-targets --features "enable_env_logger benchmark" -- -D warnings -A unknown-lints lint-kotlin: ## Run ktlint to lint Kotlin code ./gradlew lint ktlint detekt diff --git a/glean-core/Cargo.toml b/glean-core/Cargo.toml index 8ae43158d8..972ec4ceb8 100644 --- a/glean-core/Cargo.toml +++ b/glean-core/Cargo.toml @@ -46,6 +46,7 @@ malloc_size_of_derive = "0.1.3" malloc_size_of = { version = "0.2.2", package = "wr_malloc_size_of", default-features = false, features = ["once_cell"] } rusqlite = { version = "0.37.0", features = ["bundled"], optional = true } rmp-serde = "1.3.1" +gecko-profiler = { version = "0.1.0", optional = true } [target.'cfg(target_os = "android")'.dependencies] android_logger = { version = "0.12.0", default-features = false } @@ -71,7 +72,7 @@ uniffi = { version = "0.32.0", default-features = false, features = ["build"] } # Enable `env_logger`. Only works on non-Android non-iOS targets. enable_env_logger = ["env_logger"] # Enable gecko-specific APIs -gecko = [] +gecko = ["dep:gecko-profiler"] # Expose some internals for easier benchmarking benchmark = [] # Explicitly link against m-c libraries diff --git a/glean-core/src/database/rkv.rs b/glean-core/src/database/rkv.rs index bddbb1158b..ff3f8d4d81 100644 --- a/glean-core/src/database/rkv.rs +++ b/glean-core/src/database/rkv.rs @@ -17,6 +17,11 @@ use std::sync::atomic::{AtomicUsize, Ordering}; use std::sync::{Mutex, RwLock}; use std::time::{Duration, Instant}; +#[cfg(feature = "gecko")] +use gecko_profiler::{ + gecko_profiler_category, lazy_add_marker, MarkerOptions, MarkerTiming, ProfilerMarker, + ProfilerTime, +}; use malloc_size_of::MallocSizeOf; use rkv::{StoreError, StoreOptions}; @@ -37,8 +42,29 @@ macro_rules! unwrap_or { }; } +#[cfg(feature = "gecko")] +#[derive(serde::Serialize, serde::Deserialize)] +pub struct TimingMarker; + +#[cfg(feature = "gecko")] +impl ProfilerMarker for TimingMarker { + fn marker_type_name() -> &'static str { + "TimingMarker" + } + + fn marker_type_display() -> gecko_profiler::MarkerSchema { + use gecko_profiler::schema::*; + let schema = MarkerSchema::new(&[Location::MarkerChart, Location::MarkerTable]); + schema + } + + fn stream_json_marker_data(&self, _json_writer: &mut gecko_profiler::JSONWriter) {} +} + macro_rules! measure_commit { ($this:ident, $expr:expr) => {{ + #[cfg(feature = "gecko")] + let profiler_start = ProfilerTime::now(); let now = ::std::time::Instant::now(); let res = $expr; let elapsed = now.elapsed(); @@ -46,6 +72,16 @@ macro_rules! measure_commit { let mut samples = $this.write_timings.borrow_mut(); samples.push(elapsed); } + #[cfg(feature = "gecko")] + lazy_add_marker!( + "glean-core::commit", + gecko_profiler_category!(Telemetry), + MarkerOptions { + timing: MarkerTiming::interval_until_now_from(profiler_start), + ..Default::default() + }, + TimingMarker + ); res }}; } diff --git a/supply-chain/config.toml b/supply-chain/config.toml index 4ebd269c0d..67f2b0d4db 100644 --- a/supply-chain/config.toml +++ b/supply-chain/config.toml @@ -79,6 +79,10 @@ criteria = "safe-to-deploy" version = "2.9.0" criteria = "safe-to-deploy" +[[exemptions.gecko-profiler]] +version = "0.1.0" +criteria = "safe-to-deploy" + [[exemptions.getrandom]] version = "0.2.8" criteria = "safe-to-deploy" From 50ccdf73b0bcbd844281204e1147fc93a2546f78 Mon Sep 17 00:00:00 2001 From: Jan-Erik Rediger Date: Mon, 5 Oct 2026 13:02:23 +0200 Subject: [PATCH 2/2] Profile markers for SQLite commits --- glean-core/src/database/sqlite/connection.rs | 40 ++++++++++++++++++++ 1 file changed, 40 insertions(+) diff --git a/glean-core/src/database/sqlite/connection.rs b/glean-core/src/database/sqlite/connection.rs index badf86f531..d7ef826eb1 100644 --- a/glean-core/src/database/sqlite/connection.rs +++ b/glean-core/src/database/sqlite/connection.rs @@ -10,6 +10,11 @@ use std::sync::{Mutex, MutexGuard}; use std::{fmt::Debug, num::NonZeroU32, path::Path}; +#[cfg(feature = "gecko")] +use gecko_profiler::{ + gecko_profiler_category, lazy_add_marker, MarkerOptions, MarkerTiming, ProfilerMarker, + ProfilerTime, +}; use rusqlite::{OpenFlags, Transaction, TransactionBehavior}; /// Sets up an SQLite database connection, and either @@ -113,11 +118,46 @@ impl Connection { let mut conn = self.conn.lock().unwrap(); let mut tx = conn.transaction_with_behavior(TransactionBehavior::Immediate)?; let result = f(&mut tx)?; + + #[cfg(feature = "gecko")] + let profiler_start = ProfilerTime::now(); + tx.commit()?; + + #[cfg(feature = "gecko")] + lazy_add_marker!( + "glean-core::sqlite-commit", + gecko_profiler_category!(Telemetry), + MarkerOptions { + timing: MarkerTiming::interval_until_now_from(profiler_start), + ..Default::default() + }, + TimingMarker + ); + Ok(result) } } +#[cfg(feature = "gecko")] +#[derive(serde::Serialize, serde::Deserialize)] +pub struct TimingMarker; + +#[cfg(feature = "gecko")] +impl ProfilerMarker for TimingMarker { + fn marker_type_name() -> &'static str { + "TimingMarker" + } + + fn marker_type_display() -> gecko_profiler::MarkerSchema { + use gecko_profiler::schema::*; + let schema = MarkerSchema::new(&[Location::MarkerChart, Location::MarkerTable]); + schema + } + + fn stream_json_marker_data(&self, _json_writer: &mut gecko_profiler::JSONWriter) {} +} + impl Debug for Connection { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { f.write_str("Connection { .. }")