mirror of https://github.com/SixLabors/ImageSharp
4 changed files with 103 additions and 231 deletions
@ -1,88 +0,0 @@ |
|||||
// Copyright (c) Six Labors.
|
|
||||
// Licensed under the Six Labors Split License.
|
|
||||
|
|
||||
using CommandLine; |
|
||||
using CommandLine.Text; |
|
||||
|
|
||||
namespace SixLabors.ImageSharp.Tests.ProfilingSandbox; |
|
||||
|
|
||||
public partial class ParallelProcessingStress |
|
||||
{ |
|
||||
public static void RunExperiment(string[] args) |
|
||||
{ |
|
||||
ExperimentOptions options = null; |
|
||||
using Parser parser = new(settings => settings.CaseInsensitiveEnumValues = true); |
|
||||
ParserResult<ExperimentOptions> result = parser.ParseArguments<ExperimentOptions>(args).WithParsed(o => options = o); |
|
||||
if (options == null) |
|
||||
{ |
|
||||
Console.WriteLine(HelpText.RenderUsageText(result)); |
|
||||
return; |
|
||||
} |
|
||||
|
|
||||
RunExperiment(options.Method, options.Seconds, options.IterationCount); |
|
||||
} |
|
||||
|
|
||||
public static void RunExperiment(Method method, int seconds = 5, int times = 5) |
|
||||
{ |
|
||||
// Warmup
|
|
||||
Console.WriteLine("Warming up..."); |
|
||||
CommandLineOptions warmupOptions = new() { Method = method, Seconds = 1 }; |
|
||||
warmupOptions.Normalize(); |
|
||||
new ParallelProcessingStress(warmupOptions).Run(); |
|
||||
|
|
||||
// Outer loop: run inner loop for each parallelism level
|
|
||||
List<(int Parallelism, double AvgMpxPerSecPerCpu)> results = new(); |
|
||||
|
|
||||
foreach (int parallelism in ParallelismLevels()) |
|
||||
{ |
|
||||
Console.WriteLine($"\nRunning {method} with ProcessorParallelism={parallelism} ({times}x {seconds}s)..."); |
|
||||
|
|
||||
double totalMpxPerSecPerCpu = 0; |
|
||||
for (int i = 0; i < times; i++) |
|
||||
{ |
|
||||
CommandLineOptions options = new() { Method = method, ProcessorParallelism = parallelism, Seconds = seconds }; |
|
||||
options.Normalize(); |
|
||||
Stats stats = new ParallelProcessingStress(options).Run(); |
|
||||
totalMpxPerSecPerCpu += stats.MegapixelsPerSecPerCpu; |
|
||||
} |
|
||||
|
|
||||
results.Add((parallelism, totalMpxPerSecPerCpu / times)); |
|
||||
} |
|
||||
|
|
||||
// Print results as markdown table
|
|
||||
Console.WriteLine(); |
|
||||
Console.WriteLine("| ProcessorParallelism | MegapixelsPerSecPerCpu |"); |
|
||||
Console.WriteLine("|---------------------:|-----------------------:|"); |
|
||||
foreach ((int parallelism, double avg) in results) |
|
||||
{ |
|
||||
Console.WriteLine($"| {parallelism,20} | {avg,22:f3} |"); |
|
||||
} |
|
||||
} |
|
||||
|
|
||||
private sealed class ExperimentOptions |
|
||||
{ |
|
||||
[Option('m', "method", Required = false, Default = Method.Edges, HelpText = "The stress test method to run (Edges, Crop)")] |
|
||||
public Method Method { get; set; } = Method.Edges; |
|
||||
|
|
||||
[Option('s', "seconds", Required = false, Default = 5, HelpText = "Duration of each run in seconds")] |
|
||||
public int Seconds { get; set; } = 5; |
|
||||
|
|
||||
[Option('i', "iterations", Required = false, Default = 5, HelpText = "Number of runs per parallelism level")] |
|
||||
public int IterationCount { get; set; } = 5; |
|
||||
} |
|
||||
|
|
||||
private static IEnumerable<int> ParallelismLevels() |
|
||||
{ |
|
||||
int cpuCount = Environment.ProcessorCount; |
|
||||
for (int p = 1; p <= cpuCount; p *= 2) |
|
||||
{ |
|
||||
yield return p; |
|
||||
} |
|
||||
|
|
||||
// When cpuCount is not a power of two, append it as the final step
|
|
||||
if ((cpuCount & (cpuCount - 1)) != 0) |
|
||||
{ |
|
||||
yield return cpuCount; |
|
||||
} |
|
||||
} |
|
||||
} |
|
||||
@ -1,73 +1,38 @@ |
|||||
// Copyright (c) Six Labors.
|
// Copyright (c) Six Labors.
|
||||
// Licensed under the Six Labors Split License.
|
// Licensed under the Six Labors Split License.
|
||||
|
|
||||
using System.Reflection; |
|
||||
using SixLabors.ImageSharp.Tests.PixelFormats.PixelOperations; |
using SixLabors.ImageSharp.Tests.PixelFormats.PixelOperations; |
||||
using SixLabors.ImageSharp.Tests.ProfilingBenchmarks; |
using SixLabors.ImageSharp.Tests.ProfilingBenchmarks; |
||||
|
using SixLabors.ImageSharp.Tests.ProfilingSandbox; |
||||
using Xunit.Abstractions; |
using Xunit.Abstractions; |
||||
|
|
||||
// in this file, comments are used for disabling stuff for local execution
|
// in this file, comments are used for disabling stuff for local execution
|
||||
#pragma warning disable SA1515
|
#pragma warning disable SA1515
|
||||
#pragma warning disable SA1512
|
#pragma warning disable SA1512
|
||||
|
|
||||
namespace SixLabors.ImageSharp.Tests.ProfilingSandbox; |
// LoadResizeSaveParallelMemoryStress.Run(args);
|
||||
|
// ParallelProcessingStress.RunExperiment(args);
|
||||
|
// ParallelProcessingStress.Run(args);
|
||||
|
await ProcessorThroughputTest.RunAsync(args); |
||||
|
|
||||
public class Program |
// RunToVector4ProfilingTest();
|
||||
{ |
// RunResizeProfilingTest();
|
||||
private sealed class ConsoleOutput : ITestOutputHelper |
|
||||
{ |
|
||||
public void WriteLine(string message) => Console.WriteLine(message); |
|
||||
|
|
||||
public void WriteLine(string format, params object[] args) => Console.WriteLine(format, args); |
|
||||
} |
|
||||
|
|
||||
/// <summary>
|
|
||||
/// The main entry point. Useful for executing benchmarks and performance unit tests manually,
|
|
||||
/// when the IDE test runners lack some of the functionality. Eg.: it's not possible to run JetBrains memory profiler for unit tests.
|
|
||||
/// </summary>
|
|
||||
/// <param name="args">
|
|
||||
/// The arguments to pass to the program.
|
|
||||
/// </param>
|
|
||||
public static void Main(string[] args) |
|
||||
{ |
|
||||
try |
|
||||
{ |
|
||||
// LoadResizeSaveParallelMemoryStress.Run(args);
|
|
||||
ParallelProcessingStress.RunExperiment(args); |
|
||||
// ParallelProcessingStress.Run(args);
|
|
||||
} |
|
||||
catch (Exception ex) |
|
||||
{ |
|
||||
Console.WriteLine(ex); |
|
||||
} |
|
||||
|
|
||||
// RunToVector4ProfilingTest();
|
static void RunResizeProfilingTest() |
||||
// RunResizeProfilingTest();
|
{ |
||||
} |
ResizeProfilingBenchmarks test = new(new ConsoleOutput()); |
||||
|
test.ResizeBicubic(4000, 4000); |
||||
private static Version GetNetCoreVersion() |
} |
||||
{ |
|
||||
Assembly assembly = typeof(System.Runtime.GCSettings).GetTypeInfo().Assembly; |
|
||||
Console.WriteLine(assembly.Location); |
|
||||
string[] assemblyPath = assembly.Location.Split(['/', '\\'], StringSplitOptions.RemoveEmptyEntries); |
|
||||
int netCoreAppIndex = Array.IndexOf(assemblyPath, "Microsoft.NETCore.App"); |
|
||||
if (netCoreAppIndex > 0 && netCoreAppIndex < assemblyPath.Length - 2) |
|
||||
{ |
|
||||
return Version.Parse(assemblyPath[netCoreAppIndex + 1]); |
|
||||
} |
|
||||
|
|
||||
return null; |
static void RunToVector4ProfilingTest() |
||||
} |
{ |
||||
|
PixelOperationsTests.Rgba32_OperationsTests tests = new(new ConsoleOutput()); |
||||
|
tests.Benchmark_ToVector4(); |
||||
|
} |
||||
|
|
||||
private static void RunResizeProfilingTest() |
sealed class ConsoleOutput : ITestOutputHelper |
||||
{ |
{ |
||||
ResizeProfilingBenchmarks test = new(new ConsoleOutput()); |
public void WriteLine(string message) => Console.WriteLine(message); |
||||
test.ResizeBicubic(4000, 4000); |
|
||||
} |
|
||||
|
|
||||
private static void RunToVector4ProfilingTest() |
public void WriteLine(string format, params object[] args) => Console.WriteLine(format, args); |
||||
{ |
|
||||
PixelOperationsTests.Rgba32_OperationsTests tests = new(new ConsoleOutput()); |
|
||||
tests.Benchmark_ToVector4(); |
|
||||
} |
|
||||
} |
} |
||||
|
|||||
Loading…
Reference in new issue