dev/perf-runtime-introspection-syscalls #17

Merged
bquarkz merged 6 commits from dev/perf-runtime-introspection-syscalls into master 2026-04-19 08:20:10 +00:00
7 changed files with 52 additions and 8 deletions
Showing only changes of commit c87a1b7f62 - Show all commits

View File

@ -68,6 +68,8 @@ pub enum DebugEvent {
glyph_slots_total: u32, glyph_slots_total: u32,
sound_slots_used: u32, sound_slots_used: u32,
sound_slots_total: u32, sound_slots_total: u32,
scene_slots_used: u32,
scene_slots_total: u32,
}, },
#[serde(rename = "fault")] #[serde(rename = "fault")]
Fault { Fault {
@ -99,6 +101,8 @@ mod tests {
glyph_slots_total: 16, glyph_slots_total: 16,
sound_slots_used: 2, sound_slots_used: 2,
sound_slots_total: 16, sound_slots_total: 16,
scene_slots_used: 3,
scene_slots_total: 16,
}; };
let json = serde_json::to_string(&event).unwrap(); let json = serde_json::to_string(&event).unwrap();

View File

@ -1,8 +1,7 @@
use crate::syscalls::{Syscall, SyscallRegistryEntry, caps}; use crate::syscalls::{Syscall, SyscallRegistryEntry, caps};
pub(crate) const ENTRIES: &[SyscallRegistryEntry] = &[ pub(crate) const ENTRIES: &[SyscallRegistryEntry] =
SyscallRegistryEntry::builder(Syscall::BankInfo, "bank", "info") &[SyscallRegistryEntry::builder(Syscall::BankInfo, "bank", "info")
.args(1) .args(1)
.rets(2) .rets(2)
.caps(caps::BANK), .caps(caps::BANK)];
];

View File

@ -18,6 +18,8 @@ pub struct TelemetryFrame {
pub glyph_slots_total: u32, pub glyph_slots_total: u32,
pub sound_slots_used: u32, pub sound_slots_used: u32,
pub sound_slots_total: u32, pub sound_slots_total: u32,
pub scene_slots_used: u32,
pub scene_slots_total: u32,
// RAM (Heap) // RAM (Heap)
pub heap_used_bytes: usize, pub heap_used_bytes: usize,
@ -45,6 +47,8 @@ pub struct AtomicTelemetry {
pub glyph_slots_total: AtomicU32, pub glyph_slots_total: AtomicU32,
pub sound_slots_used: AtomicU32, pub sound_slots_used: AtomicU32,
pub sound_slots_total: AtomicU32, pub sound_slots_total: AtomicU32,
pub scene_slots_used: AtomicU32,
pub scene_slots_total: AtomicU32,
// RAM (Heap) // RAM (Heap)
pub heap_used_bytes: AtomicUsize, pub heap_used_bytes: AtomicUsize,
@ -75,6 +79,8 @@ impl AtomicTelemetry {
glyph_slots_total: self.glyph_slots_total.load(Ordering::Relaxed), glyph_slots_total: self.glyph_slots_total.load(Ordering::Relaxed),
sound_slots_used: self.sound_slots_used.load(Ordering::Relaxed), sound_slots_used: self.sound_slots_used.load(Ordering::Relaxed),
sound_slots_total: self.sound_slots_total.load(Ordering::Relaxed), sound_slots_total: self.sound_slots_total.load(Ordering::Relaxed),
scene_slots_used: self.scene_slots_used.load(Ordering::Relaxed),
scene_slots_total: self.scene_slots_total.load(Ordering::Relaxed),
heap_used_bytes: self.heap_used_bytes.load(Ordering::Relaxed), heap_used_bytes: self.heap_used_bytes.load(Ordering::Relaxed),
heap_max_bytes: self.heap_max_bytes.load(Ordering::Relaxed), heap_max_bytes: self.heap_max_bytes.load(Ordering::Relaxed),
logs_count: self.logs_count.load(Ordering::Relaxed), logs_count: self.logs_count.load(Ordering::Relaxed),
@ -93,6 +99,8 @@ impl AtomicTelemetry {
self.glyph_slots_total.store(0, Ordering::Relaxed); self.glyph_slots_total.store(0, Ordering::Relaxed);
self.sound_slots_used.store(0, Ordering::Relaxed); self.sound_slots_used.store(0, Ordering::Relaxed);
self.sound_slots_total.store(0, Ordering::Relaxed); self.sound_slots_total.store(0, Ordering::Relaxed);
self.scene_slots_used.store(0, Ordering::Relaxed);
self.scene_slots_total.store(0, Ordering::Relaxed);
self.heap_used_bytes.store(0, Ordering::Relaxed); self.heap_used_bytes.store(0, Ordering::Relaxed);
self.vm_steps.store(0, Ordering::Relaxed); self.vm_steps.store(0, Ordering::Relaxed);
self.logs_count.store(0, Ordering::Relaxed); self.logs_count.store(0, Ordering::Relaxed);

View File

@ -7,7 +7,9 @@ use prometeu_vm::LogicalFrameEndingReason;
use std::sync::atomic::Ordering; use std::sync::atomic::Ordering;
impl VirtualMachineRuntime { impl VirtualMachineRuntime {
fn bank_telemetry_summary(hw: &dyn HardwareBridge) -> (BankTelemetry, BankTelemetry) { fn bank_telemetry_summary(
hw: &dyn HardwareBridge,
) -> (BankTelemetry, BankTelemetry, BankTelemetry) {
let telemetry = hw.assets().bank_telemetry(); let telemetry = hw.assets().bank_telemetry();
let glyph = let glyph =
telemetry.iter().find(|entry| entry.bank_type == BankType::GLYPH).cloned().unwrap_or( telemetry.iter().find(|entry| entry.bank_type == BankType::GLYPH).cloned().unwrap_or(
@ -17,8 +19,12 @@ impl VirtualMachineRuntime {
telemetry.iter().find(|entry| entry.bank_type == BankType::SOUNDS).cloned().unwrap_or( telemetry.iter().find(|entry| entry.bank_type == BankType::SOUNDS).cloned().unwrap_or(
BankTelemetry { bank_type: BankType::SOUNDS, used_slots: 0, total_slots: 0 }, BankTelemetry { bank_type: BankType::SOUNDS, used_slots: 0, total_slots: 0 },
); );
let scenes =
telemetry.iter().find(|entry| entry.bank_type == BankType::SCENE).cloned().unwrap_or(
BankTelemetry { bank_type: BankType::SCENE, used_slots: 0, total_slots: 0 },
);
(glyph, sounds) (glyph, sounds, scenes)
} }
pub fn debug_step_instruction( pub fn debug_step_instruction(
@ -148,7 +154,7 @@ impl VirtualMachineRuntime {
hw.render_frame(); hw.render_frame();
// 1. Snapshot full telemetry at logical frame end // 1. Snapshot full telemetry at logical frame end
let (glyph_bank, sound_bank) = Self::bank_telemetry_summary(hw); let (glyph_bank, sound_bank, scene_bank) = Self::bank_telemetry_summary(hw);
self.atomic_telemetry self.atomic_telemetry
.glyph_slots_used .glyph_slots_used
.store(glyph_bank.used_slots as u32, Ordering::Relaxed); .store(glyph_bank.used_slots as u32, Ordering::Relaxed);
@ -161,6 +167,12 @@ impl VirtualMachineRuntime {
self.atomic_telemetry self.atomic_telemetry
.sound_slots_total .sound_slots_total
.store(sound_bank.total_slots as u32, Ordering::Relaxed); .store(sound_bank.total_slots as u32, Ordering::Relaxed);
self.atomic_telemetry
.scene_slots_used
.store(scene_bank.used_slots as u32, Ordering::Relaxed);
self.atomic_telemetry
.scene_slots_total
.store(scene_bank.total_slots as u32, Ordering::Relaxed);
self.atomic_telemetry self.atomic_telemetry
.heap_used_bytes .heap_used_bytes
@ -218,7 +230,7 @@ impl VirtualMachineRuntime {
// 2. High-frequency telemetry update (only if inspection is active) // 2. High-frequency telemetry update (only if inspection is active)
if self.inspection_active { if self.inspection_active {
let (glyph_bank, sound_bank) = Self::bank_telemetry_summary(hw); let (glyph_bank, sound_bank, scene_bank) = Self::bank_telemetry_summary(hw);
self.atomic_telemetry self.atomic_telemetry
.glyph_slots_used .glyph_slots_used
.store(glyph_bank.used_slots as u32, Ordering::Relaxed); .store(glyph_bank.used_slots as u32, Ordering::Relaxed);
@ -231,6 +243,12 @@ impl VirtualMachineRuntime {
self.atomic_telemetry self.atomic_telemetry
.sound_slots_total .sound_slots_total
.store(sound_bank.total_slots as u32, Ordering::Relaxed); .store(sound_bank.total_slots as u32, Ordering::Relaxed);
self.atomic_telemetry
.scene_slots_used
.store(scene_bank.used_slots as u32, Ordering::Relaxed);
self.atomic_telemetry
.scene_slots_total
.store(scene_bank.total_slots as u32, Ordering::Relaxed);
self.atomic_telemetry self.atomic_telemetry
.heap_used_bytes .heap_used_bytes

View File

@ -294,6 +294,8 @@ impl HostDebugger {
glyph_slots_total: telemetry.glyph_slots_total, glyph_slots_total: telemetry.glyph_slots_total,
sound_slots_used: telemetry.sound_slots_used, sound_slots_used: telemetry.sound_slots_used,
sound_slots_total: telemetry.sound_slots_total, sound_slots_total: telemetry.sound_slots_total,
scene_slots_used: telemetry.scene_slots_used,
scene_slots_total: telemetry.scene_slots_total,
} }
} }

View File

@ -94,6 +94,7 @@ pub(crate) fn capture_snapshot(stats: &HostStats, firmware: &Firmware) -> Overla
let heap_ratio = ratio(tel.heap_used_bytes as u64, heap_total_bytes as u64); let heap_ratio = ratio(tel.heap_used_bytes as u64, heap_total_bytes as u64);
let glyph_ratio = ratio(tel.glyph_slots_used as u64, tel.glyph_slots_total as u64); let glyph_ratio = ratio(tel.glyph_slots_used as u64, tel.glyph_slots_total as u64);
let sound_ratio = ratio(tel.sound_slots_used as u64, tel.sound_slots_total as u64); let sound_ratio = ratio(tel.sound_slots_used as u64, tel.sound_slots_total as u64);
let scene_ratio = ratio(tel.scene_slots_used as u64, tel.scene_slots_total as u64);
OverlaySnapshot { OverlaySnapshot {
rows: vec![ rows: vec![
@ -163,6 +164,12 @@ pub(crate) fn capture_snapshot(stats: &HostStats, firmware: &Firmware) -> Overla
ratio: sound_ratio, ratio: sound_ratio,
warn: tel.sound_slots_total > 0 && tel.sound_slots_used >= tel.sound_slots_total, warn: tel.sound_slots_total > 0 && tel.sound_slots_used >= tel.sound_slots_total,
}, },
OverlayBar {
label: "SCENE",
value: format!("{} / {} slots", tel.scene_slots_used, tel.scene_slots_total),
ratio: scene_ratio,
warn: tel.scene_slots_total > 0 && tel.scene_slots_used >= tel.scene_slots_total,
},
], ],
footer, footer,
} }

View File

@ -387,6 +387,8 @@ mod tests {
glyph_slots_total: 16, glyph_slots_total: 16,
sound_slots_used: 0, sound_slots_used: 0,
sound_slots_total: 8, sound_slots_total: 8,
scene_slots_used: 2,
scene_slots_total: 16,
..Default::default() ..Default::default()
}; };
@ -403,6 +405,8 @@ mod tests {
glyph_slots_total, glyph_slots_total,
sound_slots_used, sound_slots_used,
sound_slots_total, sound_slots_total,
scene_slots_used,
scene_slots_total,
} => { } => {
assert_eq!(frame_index, 8); assert_eq!(frame_index, 8);
assert_eq!(vm_steps, 123); assert_eq!(vm_steps, 123);
@ -415,6 +419,8 @@ mod tests {
assert_eq!(glyph_slots_total, 16); assert_eq!(glyph_slots_total, 16);
assert_eq!(sound_slots_used, 0); assert_eq!(sound_slots_used, 0);
assert_eq!(sound_slots_total, 8); assert_eq!(sound_slots_total, 8);
assert_eq!(scene_slots_used, 2);
assert_eq!(scene_slots_total, 16);
} }
other => panic!("unexpected telemetry event: {:?}", other), other => panic!("unexpected telemetry event: {:?}", other),
} }