From 4fae77ed1c62ad6fbd1adebe83194b76e7f67be3 Mon Sep 17 00:00:00 2001 From: teinarss Date: Tue, 30 Apr 2019 22:41:45 +0200 Subject: [PATCH] Writing benchmark data at the end of the game --- OpenRA.Game/Game.cs | 46 +++++++++++--- OpenRA.Game/Support/Benchmark.cs | 62 +++++++++++++++++++ OpenRA.Game/Support/LaunchArguments.cs | 7 ++- OpenRA.Game/World.cs | 2 + .../LoadScreens/BlankLoadScreen.cs | 17 ++--- 5 files changed, 116 insertions(+), 18 deletions(-) create mode 100644 OpenRA.Game/Support/Benchmark.cs diff --git a/OpenRA.Game/Game.cs b/OpenRA.Game/Game.cs index f076f0d6fa..73e8e5c536 100644 --- a/OpenRA.Game/Game.cs +++ b/OpenRA.Game/Game.cs @@ -51,13 +51,12 @@ namespace OpenRA public static Sound Sound; public static bool HasInputFocus = false; - public static bool BenchmarkMode = false; - public static string EngineVersion { get; private set; } public static LocalPlayerProfile LocalPlayerProfile; static Task discoverNat; static bool takeScreenshot = false; + static Benchmark benchmark = null; public static event Action OnShellmapLoaded = () => { }; @@ -167,6 +166,8 @@ namespace OpenRA using (new PerfTimer("NewWorld")) OrderManager.World = new World(ModData, map, OrderManager, type); + OrderManager.World.GameOver += FinishBenchmark; + worldRenderer = new WorldRenderer(ModData, OrderManager.World); GC.Collect(); @@ -593,9 +594,6 @@ namespace OpenRA Log.Write("debug", "--Tick: {0} ({1})", LocalTick, isNetTick ? "net" : "local"); - if (BenchmarkMode) - Log.Write("cpu", "{0};{1}".F(LocalTick, PerfHistory.Items["tick_time"].LastValue)); - if (isNetTick) orderManager.Tick(); @@ -615,6 +613,9 @@ namespace OpenRA if (orderManager.LocalFrameNumber > 0) Sync.RunUnsynced(Settings.Debug.SyncCheckUnsyncedCode, world, () => world.TickRender(worldRenderer)); } + + if (benchmark != null) + benchmark.Tick(LocalTick); } } @@ -691,9 +692,6 @@ namespace OpenRA PerfHistory.Items["batches"].Tick(); PerfHistory.Items["render_widgets"].Tick(); PerfHistory.Items["render_flip"].Tick(); - - if (BenchmarkMode) - Log.Write("render", "{0};{1}".F(RenderFrame, PerfHistory.Items["render"].LastValue)); } static void Loop() @@ -904,5 +902,37 @@ namespace OpenRA { return Renderer.Window.SetClipboardText(text); } + + public static void BenchmarkMode(string prefix) + { + benchmark = new Benchmark(prefix); + } + + public static void LoadMap(string launchMap) + { + var orders = new List + { + Order.Command("option gamespeed {0}".F("default")), + Order.Command("state {0}".F(Session.ClientState.Ready)) + }; + + var path = Platform.ResolvePath(launchMap); + var map = ModData.MapCache.SingleOrDefault(m => m.Uid == launchMap) ?? + ModData.MapCache.SingleOrDefault(m => m.Package.Name == path); + + if (map == null) + throw new InvalidOperationException("Could not find map '{0}'.".F(launchMap)); + + CreateAndStartLocalServer(map.Uid, orders); + } + + public static void FinishBenchmark() + { + if (benchmark != null) + { + benchmark.Write(); + Exit(); + } + } } } diff --git a/OpenRA.Game/Support/Benchmark.cs b/OpenRA.Game/Support/Benchmark.cs new file mode 100644 index 0000000000..1f65bb4764 --- /dev/null +++ b/OpenRA.Game/Support/Benchmark.cs @@ -0,0 +1,62 @@ +#region Copyright & License Information +/* + * Copyright 2007-2019 The OpenRA Developers (see AUTHORS) + * This file is part of OpenRA, which is free software. It is made + * available to you under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. For more + * information, see COPYING. + */ +#endregion + +using System.Collections.Generic; + +namespace OpenRA.Support +{ + class Benchmark + { + readonly string prefix; + readonly Dictionary> samples = new Dictionary>(); + + public Benchmark(string prefix) + { + this.prefix = prefix; + } + + public void Tick(int localTick) + { + foreach (var item in PerfHistory.Items) + samples.GetOrAdd(item.Key).Add(new BenchmarkPoint(localTick, item.Value.LastValue)); + } + + class BenchmarkPoint + { + public int Tick { get; private set; } + public double Value { get; private set; } + + public BenchmarkPoint(int tick, double value) + { + Tick = tick; + Value = value; + } + } + + public void Write() + { + foreach (var sample in samples) + { + var name = sample.Key; + Log.AddChannel(name, "{0}{1}.csv".F(prefix, name)); + Log.Write(name, "tick,time [ms]"); + + foreach (var point in sample.Value) + Log.Write(name, "{0},{1}".F(point.Tick, point.Value)); + } + } + + public void Reset() + { + samples.Clear(); + } + } +} diff --git a/OpenRA.Game/Support/LaunchArguments.cs b/OpenRA.Game/Support/LaunchArguments.cs index e7d35ab891..902ce5f99c 100644 --- a/OpenRA.Game/Support/LaunchArguments.cs +++ b/OpenRA.Game/Support/LaunchArguments.cs @@ -22,8 +22,11 @@ namespace OpenRA [Desc("Automatically start playing the given replay file.")] public string Replay; - [Desc("Dump performance data into cpu.csv and render.csv in the logs folder.")] - public bool Benchmark; + [Desc("Dump performance data into cpu.csv and render.csv in the logs folder with the given prefix.")] + public string Benchmark; + + [Desc("Automatically start playing the given map.")] + public string Map; public LaunchArguments(Arguments args) { diff --git a/OpenRA.Game/World.cs b/OpenRA.Game/World.cs index f1c3b74587..c7f1619d9f 100644 --- a/OpenRA.Game/World.cs +++ b/OpenRA.Game/World.cs @@ -565,6 +565,8 @@ namespace OpenRA // Actor disposals are done in a FrameEndTask while (frameEndActions.Count != 0) frameEndActions.Dequeue()(this); + + Game.FinishBenchmark(); } } diff --git a/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs b/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs index 4def6cf198..584542c1e9 100644 --- a/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs +++ b/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs @@ -45,17 +45,11 @@ namespace OpenRA.Mods.Common.LoadScreens Ui.ResetAll(); Game.Settings.Save(); - if (Launch.Benchmark) + if (!string.IsNullOrEmpty(Launch.Benchmark)) { - Log.AddChannel("cpu", "cpu.csv"); - Log.Write("cpu", "tick;time [ms]"); - - Log.AddChannel("render", "render.csv"); - Log.Write("render", "frame;time [ms]"); - Console.WriteLine("Saving benchmark data into {0}".F(Path.Combine(Platform.SupportDir, "Logs"))); - Game.BenchmarkMode = true; + Game.BenchmarkMode(Launch.Benchmark); } // Join a server directly @@ -74,6 +68,13 @@ namespace OpenRA.Mods.Common.LoadScreens } } + // Start a map directly + if (!string.IsNullOrEmpty(Launch.Map)) + { + Game.LoadMap(Launch.Map); + return; + } + // Load a replay directly if (!string.IsNullOrEmpty(Launch.Replay)) {