Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
TickProfiler
Valheim 1.0 performance profiler with real-time TPS deadlines, hitch forensics, safe mod attribution, runtime context and client graphs.
By MagiCorp
| Date uploaded | a week ago |
| Version | 1.0.1 |
| Download link | MagiCorp-TickProfiler-1.0.1.zip |
| Downloads | 27 |
| Dependency string | MagiCorp-TickProfiler-1.0.1 |
This mod requires the following mods to function
denikson-BepInExPack_Valheim
BepInEx pack for Valheim. Preconfigured with the correct entry point for mods and preferred defaults for the community.
Preferred version: 5.4.2350README
MagiCorp Valheim TickProfiler
TickProfiler 1.0 is a Valheim dedicated-server and client performance profiler focused on real-time tick deadlines, main-thread hitches, and safe mod attribution.
Server profiler
The dedicated-server component records:
- Effective 50 Hz FixedUpdate rate based on real wall-clock deadlines. Unity catch-up bursts never repay deadlines that were already missed.
- Correct pending-deadline accounting when a stall crosses a report boundary.
- Main Update throughput, p95/p99/worst gaps, stall count, excess wall time and cumulative hitch buckets.
- Event-correlated hitch attribution with confidence levels. Managed GC is reported as observed during a hitch rather than automatically blamed.
- Safe BepInEx plugin-loop attribution for
Update,FixedUpdateandLateUpdate. TickProfiler never instruments another mod's Harmony Prefix/Postfix/Finalizer methods. - Harmony patch-owner context for game methods, reported as involved mods rather than assumed causes.
- Runtime context including players, ZDO count, active objects, loaded/generated zones, thread count and VM network throughput.
- Process RSS/private memory, managed heap, GC collections and CPU usage.
- TickProfiler self-overhead, timed calls/sec, output queue depth and exception-stack recovery count.
- Optional 1-in-N sampling for deep/high-frequency game methods. Aggregate rates are scaled while worst-call values remain observed values.
The first 45 seconds are ignored by default so scene/world startup does not pollute runtime hitch statistics.
Hitch forensics
Significant hitches can create JSON captures under:
BepInEx/tickprofiler-forensics/
Each capture includes the hitch duration, estimated missed fixed deadlines, attribution/confidence, runtime context and the preceding performance samples. File output is serialized on a background worker so slow storage does not block the Valheim main thread.
Output
Normal output is written to:
BepInEx/LogOutput.logBepInEx/tickprofiler-latest.txtBepInEx/tickprofiler-status.jsonBepInEx/tickprofiler-forensics/*.jsonfor qualifying hitches
Touch BepInEx/tickprofiler.request to request an immediate full snapshot. The request file is polled at a configurable low rate rather than once per frame.
Client overlay
Install the same package on a Windows Valheim client and press F8 to toggle the overlay.
The client shows:
- Local FPS/frame-gap timing, stalls, CPU, RSS, managed memory and GC activity.
- Server effective tick rate and Update rate.
- Server runtime context and TickProfiler self-overhead.
- Top server consumers.
- Rolling five-minute client and server graphs.
- Exact server hitch-event markers at the time the hitch occurred rather than only at the next periodic snapshot.
- Snapshot age, real request/reply RTT, all TickProfiler players' RTTs, and server/client protocol compatibility.
TickProfiler 1.0 uses protocol v2 while retaining legacy v1 hello/snapshot compatibility with 0.x clients/servers where possible. Overlay text is cached between refreshes to avoid allocating new strings every render frame.
Important server settings
Created in BepInEx/config/magicorp.valheim.tickprofiler.cfg:
ReportIntervalSeconds = 10OverlayIntervalSeconds = 2RequestPollSeconds = 1StartupWarmupSeconds = 45DeepGameProfiling = trueProfilePluginLoops = trueHotMethodSampleEveryN = 4TopConsumers = 12SpikeThresholdMs = 20MainThreadStallThresholdMs = 75WriteHitchForensics = trueForensicHitchThresholdMs = 100AnnounceHitchesInChat = trueAnnounceHitchesInGame = falseAnnounceHitchThresholdMs = 250AnnounceHitchCooldownSeconds = 10
ProfileModHarmonyMethods is retained only as a deprecated 0.x compatibility key and migrates to ProfilePluginLoops.
Validation
TickProfiler 1.0.0 is built against Valheim 1.0.14 and BepInExPack Valheim 5.4.2350.
The included core tests validate deadline accounting, Unity catch-up behavior, report-boundary pending misses, JSON escaping, hitch buckets and statistic resets. A spare-server burn test also validates controlled 100/250/500/1000 ms stalls, sustained overload and exception-stack recovery.
TickProfiler is diagnostic only and does not intentionally change gameplay state.
CHANGELOG
Changelog
1.0.3
- Removed routed-RPC RTT from the live latency display and telemetry.
- Server now samples Valheim/Steam transport ping directly from every connected player socket.
- F8 overlay shows Steam transport ping for all players, including players without the TickProfiler client overlay installed.
- Network/status JSON identifies these values as
steam-transport.
1.0.2
- Client overlay now uses Valheim/Steam's native socket transport ping for the local player's displayed ping.
- Routed RPC round-trip timings are explicitly labelled as RPC/game-message latency rather than network ping.
- Removes the misleading 33/66 ms quantisation caused by Valheim update/RPC scheduling on low-latency LAN connections.
1.0.1
- Replaced Valheim
GetServerPing()display with TickProfiler-owned request/reply RTT measurement. - Added live per-player RTT to the client overlay.
- Added
tickprofiler-network.jsonand per-player RTT to status JSON for dashboards. - Added configurable
PlayerPingIntervalSecondswith a 1 second default.
1.0.0
- Major TickProfiler redesign validated against Valheim 1.0.14.
- Fixed report-boundary deadline accounting so stalls cannot move missed FixedUpdate deadlines into the following clean report or be counted twice.
- Added background/serialized file output for status, text and forensic captures; the main thread no longer performs periodic disk writes.
- Reduced
tickprofiler.requestfilesystem polling from every frame to a configurable low-rate poll. - Added startup warmup and measurement-baseline reset so world/scene startup does not pollute runtime hitch, CPU or GC statistics.
- Added exception-safe plugin-loop profiling plus root-loop recovery; recovery count is exposed in self-health output.
- Added real RSS/private memory alongside managed heap memory.
- Added profiler self-overhead, timed calls/sec and output queue depth.
- Added runtime context: player count, ZDO count, active objects, loaded/generated zones, threads and VM network throughput.
- Added cumulative hitch severity buckets.
- Added confidence-labelled hitch attribution and stopped treating coincident GC as automatically causal.
- Added Harmony patch-owner context without attributing blame to patch owners.
- Added configurable 1-in-N sampling for deep/high-frequency game methods.
- Added protocol v2/version negotiation while retaining legacy v1 compatibility paths.
- Added exact hitch-event RPC markers for the client history graph.
- Added independent lightweight overlay refresh and cached client display text to reduce allocations.
- Renamed
ProfileModHarmonyMethodstoProfilePluginLoops; the old key is retained for config migration. - Added asynchronous hitch forensic JSON captures with preceding performance/runtime samples.
- Added dependency-free regression tests for tick deadlines, catch-up behavior, pending report-boundary misses, JSON escaping, hitch buckets and stat resets.
- Burn-tested on the spare Valheim 1.0.14 server using controlled 100/250/500/1000 ms stalls, sustained 8 ms/frame load, sustained 45 ms/frame overload, and an intentional plugin exception.
0.4.4
- Fixed effective server tick rate so missed real-time FixedUpdate deadlines are counted from actual wall-clock FixedUpdate gaps rather than inferred from the 30 Hz Update loop.
- Normal Unity 50 Hz physics batching on a ~30 Hz dedicated-server player loop is not penalised, while genuine 40/60/100 ms FixedUpdate gaps permanently record 1/2/4 missed deadlines.
- Effective tick rate is now capped by actual FixedUpdate throughput, so it can never report 50 Hz when fewer successful FixedUpdates ran.
- Unity catch-up bursts remain visible as raw throughput but cannot restore missed deadlines in the headline tick rate.
0.4.3
- Critical compatibility fix: TickProfiler no longer Harmony-patches other mods' Prefix/Postfix/Finalizer methods.
- Prevents early JIT/static-initializer side effects seen with Valheim Plus
FurnaceDefinitionsand similar mods. - Plugin attribution remains enabled for safe BepInEx
Update,FixedUpdate, andLateUpdateloops. - Main-thread/frame stall detection, server profiling, hitch chat alerts, and 5-minute graphs are unchanged.
0.4.2
- Simplified BepInEx logger name to
TickProfiler. - Made periodic console reports a single multiline block.
- Added timestamped separators so consecutive profiles are easy to distinguish.
- Compact, aligned top-consumer table for AMP/mobile console readability.
0.4.1
- Significant hitches are broadcast through the TickProfiler client mod into normal Valheim chat for every connected TickProfiler client.
- Added
AnnounceHitchesInChatandHitchChatTitle; chat broadcast defaults on with senderServer. - Top-left HUD hitch messages are independently configurable and default off to avoid duplicate alerts.
0.4.0
- Replaced raw FixedUpdate catch-up throughput as the primary tick metric with effective tick rate based on real-time deadlines missed during main-thread stalls. Unity catch-up FixedUpdates no longer restore the displayed tick rate.
- Added per-hitch event attribution. Long-running game/mod methods are correlated with the exact hitch window and reported by plugin, type and method when they credibly explain the stall.
- Added configurable in-game server hitch notices (
AnnounceHitchesInGame,AnnounceHitchThresholdMs,AnnounceHitchCooldownSeconds) including duration and detected cause. - Added
Game.CollectResourcesprofiling to improve attribution of periodic Unity resource cleanup. - Added client-side plugin method attribution for BepInEx Update/FixedUpdate/LateUpdate and Harmony patch methods.
- Added rolling 5-minute client graphs: local client FPS/hitch history and server effective tick-rate/hitch history.
0.3.0
- Reworked stall detection around wall-clock main-thread gaps so Unity catch-up FixedUpdate bursts can no longer hide freezes behind an apparent 50 Hz average.
- Added server main-thread stall count, worst gap, excess lost time, p99 update gap and explicit unattributed native/Unity/I/O/GC reporting.
- Added direct save-path timing for
ZDOExtraData.PrepareSaveandZNet.SaveWorldAndPlayerProfiles. - Added real client-side profiling: frame gaps, p95/p99, local main-thread stalls, lost time, process CPU, managed memory and GC counts.
- Client F8 overlay now shows local client health above the server profiler data.
0.2.4
- Fixed the client overlay on Valheim 1.0.12 by invoking non-public
ZRoutedRpc.GetServerPeerID()through runtime reflection. - Eliminates repeated
MethodAccessExceptionspam and allows the client hello/snapshot exchange to proceed.
0.2.3
- Reworked periodic server console output into a short health/stall summary plus a top-5 consumer table.
- Detailed text and JSON snapshots remain unchanged.
0.2.2
- Fixed the client overlay losing its snapshot RPC handler when Valheim replaces
ZRoutedRpcduring the frontend-to-world transition. - The client now detects each new routed-RPC instance, re-registers the snapshot handler, and immediately re-announces itself to the server.
0.2.1
- Fixed the client overlay toggle on Valheim 1.0.12 by using Valheim's
ZInputpath instead of legacyUnityEngine.Input. - Added explicit client RPC registration and first-snapshot diagnostics.
- Added server logging when an overlay client registers.
0.2.0
- Added an optional client-side overlay, toggled with F8 by default.
- Added server-to-client RPC snapshots for current Update/FixedUpdate rates, stalls, CPU/GC data and top consumers.
- Client component is read-only and performs no profiling.
- Server only sends profiler data to clients that have the overlay installed.
- Kept the dedicated server profiler and client UI as separate DLLs so IMGUI is never loaded by the server plugin.
0.1.0
- Initial release.
- Reports server Update and FixedUpdate rates.
- Detects frame/tick stalls and gap percentiles.
- Profiles Valheim networking, ZDO replication, AI, spawning, item drops, structures, world systems and supported Harmony mod patches.
- Writes periodic log output plus JSON and text snapshots.
- Supports on-demand snapshots using
BepInEx/tickprofiler.request.