diff options
Diffstat (limited to 'src')
5 files changed, 76 insertions, 8 deletions
diff --git a/src/SMAPI.Mods.ConsoleCommands/Framework/Commands/Other/PerformanceCounterCommand.cs b/src/SMAPI.Mods.ConsoleCommands/Framework/Commands/Other/PerformanceCounterCommand.cs index d49fc537..2260296b 100644 --- a/src/SMAPI.Mods.ConsoleCommands/Framework/Commands/Other/PerformanceCounterCommand.cs +++ b/src/SMAPI.Mods.ConsoleCommands/Framework/Commands/Other/PerformanceCounterCommand.cs @@ -17,6 +17,8 @@ namespace StardewModdingAPI.Mods.ConsoleCommands.Framework.Commands.Other {SubCommand.Detail, new[] {"detail", "d"}}, {SubCommand.Reset, new[] {"reset", "r"}}, {SubCommand.Trigger, new[] {"trigger"}}, + {SubCommand.Enable, new[] {"enable"}}, + {SubCommand.Disable, new[] {"disable"}}, {SubCommand.Examples, new[] {"examples"}}, {SubCommand.Concepts, new[] {"concepts"}}, {SubCommand.Help, new[] {"help"}}, @@ -29,6 +31,8 @@ namespace StardewModdingAPI.Mods.ConsoleCommands.Framework.Commands.Other Detail, Reset, Trigger, + Enable, + Disable, Examples, Help, Concepts, @@ -69,6 +73,14 @@ namespace StardewModdingAPI.Mods.ConsoleCommands.Framework.Commands.Other case SubCommand.Concepts: this.OutputHelp(monitor, SubCommand.Concepts); break; + case SubCommand.Enable: + SCore.PerformanceCounterManager.EnableTracking = true; + monitor.Log("Performance counter tracking is now enabled", LogLevel.Info); + break; + case SubCommand.Disable: + SCore.PerformanceCounterManager.EnableTracking = false; + monitor.Log("Performance counter tracking is now disabled", LogLevel.Info); + break; case SubCommand.Help: if (args.TryGet(1, "command", out string commandString)) this.OutputHelp(monitor, this.ParseCommandString(commandString)); @@ -118,20 +130,20 @@ namespace StardewModdingAPI.Mods.ConsoleCommands.Framework.Commands.Other StringBuilder sb = new StringBuilder(); - TimeSpan peakSpan = TimeSpan.FromSeconds(60); + TimeSpan interval = TimeSpan.FromSeconds(60); - sb.AppendLine("Summary:"); + sb.AppendLine($"Summary over the last {interval.TotalSeconds} seconds:"); sb.AppendLine(this.GetTableString( data: data, - header: new[] {"Collection", "Avg Calls/s", "Avg Exec Time (Game)", "Avg Exec Time (Mods)", "Avg Exec Time (Game+Mods)", "Peak Exec Time (60s)"}, + header: new[] {"Collection", "Avg Calls/s", "Avg Exec Time (Game)", "Avg Exec Time (Mods)", "Avg Exec Time (Game+Mods)", "Peak Exec Time"}, getRow: item => new[] { item.Name, item.GetAverageCallsPerSecond().ToString(), - this.FormatMilliseconds(item.GetGameAverageExecutionTime(), threshold), - this.FormatMilliseconds(item.GetModsAverageExecutionTime(), threshold), - this.FormatMilliseconds(item.GetAverageExecutionTime(), threshold), - this.FormatMilliseconds(item.GetPeakExecutionTime(peakSpan), threshold) + this.FormatMilliseconds(item.GetGameAverageExecutionTime(interval), threshold), + this.FormatMilliseconds(item.GetModsAverageExecutionTime(interval), threshold), + this.FormatMilliseconds(item.GetAverageExecutionTime(interval), threshold), + this.FormatMilliseconds(item.GetPeakExecutionTime(interval), threshold) }, true )); @@ -662,6 +674,8 @@ namespace StardewModdingAPI.Mods.ConsoleCommands.Framework.Commands.Other sb.AppendLine(" detail|d Shows performance counter information for a given collection"); sb.AppendLine(" reset|r Resets the performance counters"); sb.AppendLine(" trigger Configures alert triggers"); + sb.AppendLine(" enable Enables performance counter recording"); + sb.AppendLine(" disable Disables performance counter recording"); sb.AppendLine(" examples Displays various examples"); sb.AppendLine(" concepts Displays an explanation of the performance counter concepts"); sb.AppendLine(" help Displays verbose help for the available commands"); diff --git a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounter.cs b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounter.cs index 3d902e16..e9dfcb14 100644 --- a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounter.cs +++ b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounter.cs @@ -133,7 +133,7 @@ namespace StardewModdingAPI.Framework.PerformanceCounter DateTime start = relativeTo.Value.Subtract(range); - var entries = this._counter.Where(x => (x.EventTime >= start) && (x.EventTime <= relativeTo)); + var entries = this._counter.Where(x => (x.EventTime >= start) && (x.EventTime <= relativeTo)).ToList(); if (!entries.Any()) return 0; diff --git a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterCollection.cs b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterCollection.cs index fe14ebf8..f469eceb 100644 --- a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterCollection.cs +++ b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterCollection.cs @@ -82,6 +82,15 @@ namespace StardewModdingAPI.Framework.PerformanceCounter p.Key != Constants.GamePerformanceCounterName).Sum(p => p.Value.GetAverage()); } + /// <summary>Returns the average execution time for all non-game internal sources.</summary> + /// <param name="interval">The interval for which to get the average, relative to now</param> + /// <returns>The average execution time in milliseconds</returns> + public double GetModsAverageExecutionTime(TimeSpan interval) + { + return this.PerformanceCounters.Where(p => + p.Key != Constants.GamePerformanceCounterName).Sum(p => p.Value.GetAverage(interval)); + } + /// <summary>Returns the overall average execution time.</summary> /// <returns>The average execution time in milliseconds</returns> public double GetAverageExecutionTime() @@ -89,6 +98,14 @@ namespace StardewModdingAPI.Framework.PerformanceCounter return this.PerformanceCounters.Sum(p => p.Value.GetAverage()); } + /// <summary>Returns the overall average execution time.</summary> + /// <param name="interval">The interval for which to get the average, relative to now</param> + /// <returns>The average execution time in milliseconds</returns> + public double GetAverageExecutionTime(TimeSpan interval) + { + return this.PerformanceCounters.Sum(p => p.Value.GetAverage(interval)); + } + /// <summary>Returns the average execution time for game-internal sources.</summary> /// <returns>The average execution time in milliseconds</returns> public double GetGameAverageExecutionTime() @@ -99,6 +116,20 @@ namespace StardewModdingAPI.Framework.PerformanceCounter return 0; } + /// <summary>Returns the average execution time for game-internal sources.</summary> + /// <returns>The average execution time in milliseconds</returns> + public double GetGameAverageExecutionTime(TimeSpan interval) + { + if (this.PerformanceCounters.TryGetValue(Constants.GamePerformanceCounterName, out PerformanceCounter gameExecTime)) + return gameExecTime.GetAverage(interval); + + return 0; + } + + /// <summary>Returns the peak execution time</summary> + /// <param name="interval">The interval for which to get the peak, relative to <paramref name="relativeTo"/></param> + /// <param name="relativeTo">The DateTime which the <paramref name="interval"/> is relative to, or DateTime.Now if not given</param> + /// <returns>The peak execution time</returns> public double GetPeakExecutionTime(TimeSpan range, DateTime? relativeTo = null) { if (this.PeakInvocations.IsEmpty) diff --git a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterManager.cs b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterManager.cs index a8e20eda..bd964442 100644 --- a/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterManager.cs +++ b/src/SMAPI/Framework/PerformanceCounter/PerformanceCounterManager.cs @@ -23,6 +23,9 @@ namespace StardewModdingAPI.Framework.PerformanceCounter /// <summary>Specifies if alerts should be paused.</summary> public bool PauseAlerts { get; set; } + /// <summary>Specifies if performance counter tracking should be enabled.</summary> + public bool EnableTracking { get; set; } + /// <summary>Constructs a performance counter manager.</summary> /// <param name="monitor">The monitor for output logging.</param> public PerformanceCounterManager(IMonitor monitor) @@ -49,6 +52,11 @@ namespace StardewModdingAPI.Framework.PerformanceCounter /// <param name="collectionName">The collection name</param> public void BeginTrackInvocation(string collectionName) { + if (!this.EnableTracking) + { + return; + } + this.GetOrCreateCollectionByName(collectionName).BeginTrackInvocation(); } @@ -56,6 +64,11 @@ namespace StardewModdingAPI.Framework.PerformanceCounter /// <param name="collectionName"></param> public void EndTrackInvocation(string collectionName) { + if (!this.EnableTracking) + { + return; + } + this.GetOrCreateCollectionByName(collectionName).EndTrackInvocation(); } @@ -65,6 +78,12 @@ namespace StardewModdingAPI.Framework.PerformanceCounter /// <param name="action">The action to execute and track invocation time for.</param> public void Track(string collectionName, string sourceName, Action action) { + if (!this.EnableTracking) + { + action(); + return; + } + DateTime eventTime = DateTime.UtcNow; this.InvocationStopwatch.Reset(); this.InvocationStopwatch.Start(); diff --git a/src/SMAPI/SMAPI.csproj b/src/SMAPI/SMAPI.csproj index 5e407c2c..0bc290ac 100644 --- a/src/SMAPI/SMAPI.csproj +++ b/src/SMAPI/SMAPI.csproj @@ -15,6 +15,10 @@ <ApplicationIcon>icon.ico</ApplicationIcon> </PropertyGroup> + <PropertyGroup Condition=" '$(Configuration)' == 'Release' "> + <DefineConstants>SMAPI_FOR_WINDOWS</DefineConstants> + </PropertyGroup> + <ItemGroup> <PackageReference Include="Cyotek.CircularBuffer" Version="1.0.2" /> <PackageReference Include="LargeAddressAware" Version="1.0.3" /> |