xref: /llvm-project/llvm/tools/llvm-exegesis/lib/ResultAggregator.cpp (revision 415bf200a725055a3a38e96269f4b752ea6fc330)
1 //===-- ResultAggregator.cpp ------------------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "ResultAggregator.h"
10 
11 namespace llvm {
12 namespace exegesis {
13 
14 class DefaultResultAggregator : public ResultAggregator {
AggregateResults(Benchmark & Result,ArrayRef<Benchmark> OtherResults) const15   void AggregateResults(Benchmark &Result,
16                         ArrayRef<Benchmark> OtherResults) const override{};
AggregateMeasurement(BenchmarkMeasure & Measurement,const BenchmarkMeasure & NewMeasurement,const Benchmark & Result) const17   void AggregateMeasurement(BenchmarkMeasure &Measurement,
18                             const BenchmarkMeasure &NewMeasurement,
19                             const Benchmark &Result) const override{};
20 };
21 
22 class MinimumResultAggregator : public ResultAggregator {
23   void AggregateMeasurement(BenchmarkMeasure &Measurement,
24                             const BenchmarkMeasure &NewMeasurement,
25                             const Benchmark &Result) const override;
26 };
27 
AggregateMeasurement(BenchmarkMeasure & Measurement,const BenchmarkMeasure & NewMeasurement,const Benchmark & Result) const28 void MinimumResultAggregator::AggregateMeasurement(
29     BenchmarkMeasure &Measurement, const BenchmarkMeasure &NewMeasurement,
30     const Benchmark &Result) const {
31   Measurement.PerInstructionValue = std::min(
32       Measurement.PerInstructionValue, NewMeasurement.PerInstructionValue);
33   Measurement.PerSnippetValue =
34       std::min(Measurement.PerSnippetValue, NewMeasurement.PerSnippetValue);
35   Measurement.RawValue =
36       std::min(Measurement.RawValue, NewMeasurement.RawValue);
37 }
38 
39 class MiddleHalfResultAggregator : public ResultAggregator {
40   void AggregateMeasurement(BenchmarkMeasure &Measurement,
41                             const BenchmarkMeasure &NewMeasurement,
42                             const Benchmark &Result) const override;
43 };
44 
AggregateMeasurement(BenchmarkMeasure & Measurement,const BenchmarkMeasure & NewMeasurement,const Benchmark & Result) const45 void MiddleHalfResultAggregator::AggregateMeasurement(
46     BenchmarkMeasure &Measurement, const BenchmarkMeasure &NewMeasurement,
47     const Benchmark &Result) const {
48   Measurement.RawValue = NewMeasurement.RawValue - Measurement.RawValue;
49   Measurement.PerInstructionValue = Measurement.RawValue;
50   Measurement.PerInstructionValue /= Result.MinInstructions;
51   Measurement.PerSnippetValue = Measurement.RawValue;
52   Measurement.PerSnippetValue /=
53       std::ceil(Result.MinInstructions /
54                 static_cast<double>(Result.Key.Instructions.size()));
55 }
56 
AggregateResults(Benchmark & Result,ArrayRef<Benchmark> OtherResults) const57 void ResultAggregator::AggregateResults(
58     Benchmark &Result, ArrayRef<Benchmark> OtherResults) const {
59   for (const Benchmark &OtherResult : OtherResults) {
60     append_range(Result.AssembledSnippet, OtherResult.AssembledSnippet);
61 
62     if (OtherResult.Measurements.empty())
63       continue;
64 
65     assert(OtherResult.Measurements.size() == Result.Measurements.size() &&
66            "Expected to have an identical number of measurements");
67 
68     for (auto I : zip(Result.Measurements, OtherResult.Measurements)) {
69       BenchmarkMeasure &Measurement = std::get<0>(I);
70       const BenchmarkMeasure &NewMeasurement = std::get<1>(I);
71 
72       assert(Measurement.Key == NewMeasurement.Key &&
73              "Expected measurements to be symmetric");
74 
75       AggregateMeasurement(Measurement, NewMeasurement, Result);
76     }
77   }
78 }
79 
80 std::unique_ptr<ResultAggregator>
CreateAggregator(Benchmark::RepetitionModeE RepetitionMode)81 ResultAggregator::CreateAggregator(Benchmark::RepetitionModeE RepetitionMode) {
82   switch (RepetitionMode) {
83   case Benchmark::RepetitionModeE::Duplicate:
84   case Benchmark::RepetitionModeE::Loop:
85     return std::make_unique<DefaultResultAggregator>();
86   case Benchmark::RepetitionModeE::AggregateMin:
87     return std::make_unique<MinimumResultAggregator>();
88   case Benchmark::RepetitionModeE::MiddleHalfDuplicate:
89   case Benchmark::RepetitionModeE::MiddleHalfLoop:
90     return std::make_unique<MiddleHalfResultAggregator>();
91   }
92   llvm_unreachable("Unknown Benchmark::RepetitionModeE enum");
93 }
94 
95 } // namespace exegesis
96 } // namespace llvm
97