using System.Diagnostics; namespace SpaceGame.Api.Universe.Simulation; public sealed class TelemetryService : IDisposable { private readonly Process _process = Process.GetCurrentProcess(); private readonly Timer _timer; private double _cpuPercent; private DateTime _lastSampleTime; private TimeSpan _lastCpuTime; public TelemetryService() { _process.Refresh(); _lastSampleTime = DateTime.UtcNow; _lastCpuTime = _process.TotalProcessorTime; _timer = new Timer(Sample, null, TimeSpan.FromSeconds(1), TimeSpan.FromSeconds(1)); } private void Sample(object? _) { _process.Refresh(); var now = DateTime.UtcNow; var cpu = _process.TotalProcessorTime; var elapsed = (now - _lastSampleTime).TotalSeconds; var cpuUsed = (cpu - _lastCpuTime).TotalSeconds; Volatile.Write(ref _cpuPercent, elapsed > 0 ? cpuUsed / elapsed / Environment.ProcessorCount * 100.0 : 0); _lastSampleTime = now; _lastCpuTime = cpu; } public double CpuPercent => Volatile.Read(ref _cpuPercent); public long WorkingSetBytes => _process.WorkingSet64; public long GcMemoryBytes => GC.GetTotalMemory(false); public int ThreadCount => _process.Threads.Count; public TimeSpan Uptime => DateTime.UtcNow - _process.StartTime.ToUniversalTime(); public void Dispose() { _timer.Dispose(); _process.Dispose(); } }