xref: /llvm-project/llvm/tools/llvm-reduce/DeltaManager.cpp (revision 42067f26cd084d29fdd08a75a36b8785ae9f3982)
156fa1b4fSSamuel //===- DeltaManager.cpp - Runs Delta Passes to reduce Input ---------------===//
256fa1b4fSSamuel //
356fa1b4fSSamuel // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
456fa1b4fSSamuel // See https://llvm.org/LICENSE.txt for license information.
556fa1b4fSSamuel // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
656fa1b4fSSamuel //
756fa1b4fSSamuel //===----------------------------------------------------------------------===//
856fa1b4fSSamuel //
956fa1b4fSSamuel // This file calls each specialized Delta pass in order to reduce the input IR
1056fa1b4fSSamuel // file.
1156fa1b4fSSamuel //
1256fa1b4fSSamuel //===----------------------------------------------------------------------===//
1356fa1b4fSSamuel 
1456fa1b4fSSamuel #include "DeltaManager.h"
1542c7f494SClemens Wasser #include "ReducerWorkItem.h"
1656fa1b4fSSamuel #include "TestRunner.h"
1756fa1b4fSSamuel #include "deltas/Delta.h"
1856fa1b4fSSamuel #include "deltas/ReduceAliases.h"
1956fa1b4fSSamuel #include "deltas/ReduceArguments.h"
2056fa1b4fSSamuel #include "deltas/ReduceAttributes.h"
2156fa1b4fSSamuel #include "deltas/ReduceBasicBlocks.h"
222c799b77SMatthew Voss #include "deltas/ReduceDIMetadata.h"
235ff67204SStephen Tozer #include "deltas/ReduceDbgRecords.h"
24*42067f26SRobert Barinov #include "deltas/ReduceDistinctMetadata.h"
2556fa1b4fSSamuel #include "deltas/ReduceFunctionBodies.h"
2656fa1b4fSSamuel #include "deltas/ReduceFunctions.h"
2780ba72b0SArthur Eubanks #include "deltas/ReduceGlobalObjects.h"
2856fa1b4fSSamuel #include "deltas/ReduceGlobalValues.h"
2956fa1b4fSSamuel #include "deltas/ReduceGlobalVarInitializers.h"
3056fa1b4fSSamuel #include "deltas/ReduceGlobalVars.h"
313939e99aSMatt Arsenault #include "deltas/ReduceIRReferences.h"
3227902eeaSMatt Arsenault #include "deltas/ReduceInstructionFlags.h"
3320110521SMatt Arsenault #include "deltas/ReduceInstructionFlagsMIR.h"
3456fa1b4fSSamuel #include "deltas/ReduceInstructions.h"
35fd41738eSMarkus Lavin #include "deltas/ReduceInstructionsMIR.h"
36a455c916SMatt Arsenault #include "deltas/ReduceInvokes.h"
37596fdf75SMatt Arsenault #include "deltas/ReduceMemoryOperations.h"
3856fa1b4fSSamuel #include "deltas/ReduceMetadata.h"
39d2e10364SArthur Eubanks #include "deltas/ReduceModuleData.h"
40573a5de7SMatt Arsenault #include "deltas/ReduceOpcodes.h"
4156fa1b4fSSamuel #include "deltas/ReduceOperandBundles.h"
42f18c0739SSamuel #include "deltas/ReduceOperands.h"
43c15f930eSMichael Kruse #include "deltas/ReduceOperandsSkip.h"
44dd71b65cSMichael Kruse #include "deltas/ReduceOperandsToArgs.h"
45e24b390dSMatt Arsenault #include "deltas/ReduceRegisterDefs.h"
460f9d9eddSMatt Arsenault #include "deltas/ReduceRegisterMasks.h"
4747c8ec81SMatt Arsenault #include "deltas/ReduceRegisterUses.h"
4856fa1b4fSSamuel #include "deltas/ReduceSpecialGlobals.h"
492f1fa624SJohn Regehr #include "deltas/ReduceUsingSimplifyCFG.h"
50a0dcbe45SMatt Arsenault #include "deltas/ReduceVirtualRegisters.h"
51bd1f80f5SArthur Eubanks #include "deltas/RunIRPasses.h"
52eea11e73SMatt Arsenault #include "deltas/SimplifyInstructions.h"
530fbb2615SArthur Eubanks #include "deltas/StripDebugInfo.h"
54333ffafbSMatt Arsenault #include "llvm/ADT/SmallSet.h"
55545a8177SArthur Eubanks #include "llvm/Support/CommandLine.h"
5656fa1b4fSSamuel 
57545a8177SArthur Eubanks using namespace llvm;
5856fa1b4fSSamuel 
59c3bc72ccSMatt Arsenault using SmallStringSet = SmallSet<StringRef, 8>;
60c3bc72ccSMatt Arsenault 
610d36d84dSMarkus Lavin extern cl::OptionCategory LLVMReduceOptions;
62c3bc72ccSMatt Arsenault static cl::list<std::string>
63545a8177SArthur Eubanks     DeltaPasses("delta-passes",
64545a8177SArthur Eubanks                 cl::desc("Delta passes to run, separated by commas. By "
650d36d84dSMarkus Lavin                          "default, run all delta passes."),
66c3bc72ccSMatt Arsenault                 cl::cat(LLVMReduceOptions), cl::CommaSeparated);
67c3bc72ccSMatt Arsenault 
68c3bc72ccSMatt Arsenault static cl::list<std::string>
69c3bc72ccSMatt Arsenault     SkipDeltaPasses("skip-delta-passes",
70c3bc72ccSMatt Arsenault                     cl::desc("Delta passes to not run, separated by commas. By "
71c3bc72ccSMatt Arsenault                              "default, run all delta passes."),
72c3bc72ccSMatt Arsenault                     cl::cat(LLVMReduceOptions), cl::CommaSeparated);
73545a8177SArthur Eubanks 
74545a8177SArthur Eubanks #define DELTA_PASSES                                                           \
75cd434a20Sowenca   do {                                                                         \
760fbb2615SArthur Eubanks     DELTA_PASS("strip-debug-info", stripDebugInfoDeltaPass)                    \
7771d1bd14SJohn Regehr     DELTA_PASS("functions", reduceFunctionsDeltaPass)                          \
7871d1bd14SJohn Regehr     DELTA_PASS("function-bodies", reduceFunctionBodiesDeltaPass)               \
79545a8177SArthur Eubanks     DELTA_PASS("special-globals", reduceSpecialGlobalsDeltaPass)               \
80545a8177SArthur Eubanks     DELTA_PASS("aliases", reduceAliasesDeltaPass)                              \
81bc3e4923SMatt Arsenault     DELTA_PASS("ifuncs", reduceIFuncsDeltaPass)                                \
8208d1c43cSMatt Arsenault     DELTA_PASS("simplify-conditionals-true", reduceConditionalsTrueDeltaPass)  \
8340bdfd39SJeremy Morse     DELTA_PASS("simplify-conditionals-false",                                  \
8440bdfd39SJeremy Morse                reduceConditionalsFalseDeltaPass)                               \
85a455c916SMatt Arsenault     DELTA_PASS("invokes", reduceInvokesDeltaPass)                              \
8640bdfd39SJeremy Morse     DELTA_PASS("unreachable-basic-blocks",                                     \
8740bdfd39SJeremy Morse                reduceUnreachableBasicBlocksDeltaPass)                          \
88545a8177SArthur Eubanks     DELTA_PASS("basic-blocks", reduceBasicBlocksDeltaPass)                     \
8945a91c15SMatt Arsenault     DELTA_PASS("simplify-cfg", reduceUsingSimplifyCFGDeltaPass)                \
9047e44c0cSMatt Arsenault     DELTA_PASS("function-data", reduceFunctionDataDeltaPass)                   \
91545a8177SArthur Eubanks     DELTA_PASS("global-values", reduceGlobalValuesDeltaPass)                   \
9280ba72b0SArthur Eubanks     DELTA_PASS("global-objects", reduceGlobalObjectsDeltaPass)                 \
93545a8177SArthur Eubanks     DELTA_PASS("global-initializers", reduceGlobalsInitializersDeltaPass)      \
94545a8177SArthur Eubanks     DELTA_PASS("global-variables", reduceGlobalsDeltaPass)                     \
952c799b77SMatthew Voss     DELTA_PASS("di-metadata", reduceDIMetadataDeltaPass)                       \
96ababa964SOrlando Cazalet-Hyams     DELTA_PASS("dbg-records", reduceDbgRecordDeltaPass)                        \
97*42067f26SRobert Barinov     DELTA_PASS("distinct-metadata", reduceDistinctMetadataDeltaPass)           \
98545a8177SArthur Eubanks     DELTA_PASS("metadata", reduceMetadataDeltaPass)                            \
995f6bf752SMatt Arsenault     DELTA_PASS("named-metadata", reduceNamedMetadataDeltaPass)                 \
100545a8177SArthur Eubanks     DELTA_PASS("arguments", reduceArgumentsDeltaPass)                          \
101545a8177SArthur Eubanks     DELTA_PASS("instructions", reduceInstructionsDeltaPass)                    \
102eea11e73SMatt Arsenault     DELTA_PASS("simplify-instructions", simplifyInstructionsDeltaPass)         \
103bd1f80f5SArthur Eubanks     DELTA_PASS("ir-passes", runIRPassesDeltaPass)                              \
10496605639SArthur Eubanks     DELTA_PASS("operands-zero", reduceOperandsZeroDeltaPass)                   \
10596605639SArthur Eubanks     DELTA_PASS("operands-one", reduceOperandsOneDeltaPass)                     \
10626107559SMatt Arsenault     DELTA_PASS("operands-nan", reduceOperandsNaNDeltaPass)                     \
107dd71b65cSMichael Kruse     DELTA_PASS("operands-to-args", reduceOperandsToArgsDeltaPass)              \
108c15f930eSMichael Kruse     DELTA_PASS("operands-skip", reduceOperandsSkipDeltaPass)                   \
109545a8177SArthur Eubanks     DELTA_PASS("operand-bundles", reduceOperandBundesDeltaPass)                \
110545a8177SArthur Eubanks     DELTA_PASS("attributes", reduceAttributesDeltaPass)                        \
111cd434a20Sowenca     DELTA_PASS("module-data", reduceModuleDataDeltaPass)                       \
112573a5de7SMatt Arsenault     DELTA_PASS("opcodes", reduceOpcodesDeltaPass)                              \
113596fdf75SMatt Arsenault     DELTA_PASS("volatile", reduceVolatileInstructionsDeltaPass)                \
11483da1a6aSMatt Arsenault     DELTA_PASS("atomic-ordering", reduceAtomicOrderingDeltaPass)               \
115b1e17199SMatt Arsenault     DELTA_PASS("syncscopes", reduceAtomicSyncScopesDeltaPass)                  \
11627902eeaSMatt Arsenault     DELTA_PASS("instruction-flags", reduceInstructionFlagsDeltaPass)           \
117cd434a20Sowenca   } while (false)
118545a8177SArthur Eubanks 
119fd41738eSMarkus Lavin #define DELTA_PASSES_MIR                                                       \
120cd434a20Sowenca   do {                                                                         \
121853a46cfSFlorian Mayer     DELTA_PASS("instructions", reduceInstructionsMIRDeltaPass)                 \
1223939e99aSMatt Arsenault     DELTA_PASS("ir-instruction-references",                                    \
1233939e99aSMatt Arsenault                reduceIRInstructionReferencesDeltaPass)                         \
1243939e99aSMatt Arsenault     DELTA_PASS("ir-block-references", reduceIRBlockReferencesDeltaPass)        \
12520110521SMatt Arsenault     DELTA_PASS("ir-function-references", reduceIRFunctionReferencesDeltaPass)  \
126a0dcbe45SMatt Arsenault     DELTA_PASS("instruction-flags", reduceInstructionFlagsMIRDeltaPass)        \
12747c8ec81SMatt Arsenault     DELTA_PASS("register-uses", reduceRegisterUsesMIRDeltaPass)                \
128e24b390dSMatt Arsenault     DELTA_PASS("register-defs", reduceRegisterDefsMIRDeltaPass)                \
129cd434a20Sowenca     DELTA_PASS("register-hints", reduceVirtualRegisterHintsDeltaPass)          \
1300f9d9eddSMatt Arsenault     DELTA_PASS("register-masks", reduceRegisterMasksMIRDeltaPass)              \
131cd434a20Sowenca   } while (false)
132fd41738eSMarkus Lavin 
133c3bc72ccSMatt Arsenault static void runAllDeltaPasses(TestRunner &Tester,
134c3bc72ccSMatt Arsenault                               const SmallStringSet &SkipPass) {
135c3bc72ccSMatt Arsenault #define DELTA_PASS(NAME, FUNC)                                                 \
136c3bc72ccSMatt Arsenault   if (!SkipPass.count(NAME)) {                                                 \
137c3bc72ccSMatt Arsenault     FUNC(Tester);                                                              \
138c3bc72ccSMatt Arsenault   }
139fd41738eSMarkus Lavin   if (Tester.getProgram().isMIR()) {
140cd434a20Sowenca     DELTA_PASSES_MIR;
141fd41738eSMarkus Lavin   } else {
142cd434a20Sowenca     DELTA_PASSES;
143fd41738eSMarkus Lavin   }
144545a8177SArthur Eubanks #undef DELTA_PASS
14556fa1b4fSSamuel }
146545a8177SArthur Eubanks 
147545a8177SArthur Eubanks static void runDeltaPassName(TestRunner &Tester, StringRef PassName) {
148545a8177SArthur Eubanks #define DELTA_PASS(NAME, FUNC)                                                 \
149545a8177SArthur Eubanks   if (PassName == NAME) {                                                      \
150545a8177SArthur Eubanks     FUNC(Tester);                                                              \
151545a8177SArthur Eubanks     return;                                                                    \
152545a8177SArthur Eubanks   }
153fd41738eSMarkus Lavin   if (Tester.getProgram().isMIR()) {
154cd434a20Sowenca     DELTA_PASSES_MIR;
155fd41738eSMarkus Lavin   } else {
156cd434a20Sowenca     DELTA_PASSES;
157fd41738eSMarkus Lavin   }
158545a8177SArthur Eubanks #undef DELTA_PASS
159c3bc72ccSMatt Arsenault 
160c3bc72ccSMatt Arsenault   // We should have errored on unrecognized passes before trying to run
161c3bc72ccSMatt Arsenault   // anything.
162c3bc72ccSMatt Arsenault   llvm_unreachable("unknown delta pass");
163545a8177SArthur Eubanks }
164545a8177SArthur Eubanks 
165545a8177SArthur Eubanks void llvm::printDeltaPasses(raw_ostream &OS) {
166545a8177SArthur Eubanks   OS << "Delta passes (pass to `--delta-passes=` as a comma separated list):\n";
167545a8177SArthur Eubanks #define DELTA_PASS(NAME, FUNC) OS << "  " << NAME << "\n";
168fd41738eSMarkus Lavin   OS << " IR:\n";
169cd434a20Sowenca   DELTA_PASSES;
170fd41738eSMarkus Lavin   OS << " MIR:\n";
171cd434a20Sowenca   DELTA_PASSES_MIR;
172545a8177SArthur Eubanks #undef DELTA_PASS
173545a8177SArthur Eubanks }
174545a8177SArthur Eubanks 
175c3bc72ccSMatt Arsenault // Built a set of available delta passes.
176c3bc72ccSMatt Arsenault static void collectPassNames(const TestRunner &Tester,
177c3bc72ccSMatt Arsenault                              SmallStringSet &NameSet) {
178c3bc72ccSMatt Arsenault #define DELTA_PASS(NAME, FUNC) NameSet.insert(NAME);
179c3bc72ccSMatt Arsenault   if (Tester.getProgram().isMIR()) {
180c3bc72ccSMatt Arsenault     DELTA_PASSES_MIR;
181c3bc72ccSMatt Arsenault   } else {
182c3bc72ccSMatt Arsenault     DELTA_PASSES;
183c3bc72ccSMatt Arsenault   }
184c3bc72ccSMatt Arsenault #undef DELTA_PASS
185c3bc72ccSMatt Arsenault }
186c3bc72ccSMatt Arsenault 
187c3bc72ccSMatt Arsenault /// Verify all requested or skipped passes are valid names, and return them in a
188c3bc72ccSMatt Arsenault /// set.
189c3bc72ccSMatt Arsenault static SmallStringSet handlePassList(const TestRunner &Tester,
190c3bc72ccSMatt Arsenault                                      const cl::list<std::string> &PassList) {
191c3bc72ccSMatt Arsenault   SmallStringSet AllPasses;
192c3bc72ccSMatt Arsenault   collectPassNames(Tester, AllPasses);
193c3bc72ccSMatt Arsenault 
194c3bc72ccSMatt Arsenault   SmallStringSet PassSet;
195c3bc72ccSMatt Arsenault   for (StringRef PassName : PassList) {
196c3bc72ccSMatt Arsenault     if (!AllPasses.count(PassName)) {
197c3bc72ccSMatt Arsenault       errs() << "unknown pass \"" << PassName << "\"\n";
198c3bc72ccSMatt Arsenault       exit(1);
199c3bc72ccSMatt Arsenault     }
200c3bc72ccSMatt Arsenault 
201c3bc72ccSMatt Arsenault     PassSet.insert(PassName);
202c3bc72ccSMatt Arsenault   }
203c3bc72ccSMatt Arsenault 
204c3bc72ccSMatt Arsenault   return PassSet;
205c3bc72ccSMatt Arsenault }
206c3bc72ccSMatt Arsenault 
2074eec1710SJohn Regehr void llvm::runDeltaPasses(TestRunner &Tester, int MaxPassIterations) {
20835264e71SMatt Arsenault   uint64_t OldComplexity = Tester.getProgram().getComplexityScore();
209c3bc72ccSMatt Arsenault 
210c3bc72ccSMatt Arsenault   SmallStringSet RunPassSet, SkipPassSet;
211c3bc72ccSMatt Arsenault 
212c3bc72ccSMatt Arsenault   if (!DeltaPasses.empty())
213c3bc72ccSMatt Arsenault     RunPassSet = handlePassList(Tester, DeltaPasses);
214c3bc72ccSMatt Arsenault 
215c3bc72ccSMatt Arsenault   if (!SkipDeltaPasses.empty())
216c3bc72ccSMatt Arsenault     SkipPassSet = handlePassList(Tester, SkipDeltaPasses);
217c3bc72ccSMatt Arsenault 
2184eec1710SJohn Regehr   for (int Iter = 0; Iter < MaxPassIterations; ++Iter) {
219545a8177SArthur Eubanks     if (DeltaPasses.empty()) {
220c3bc72ccSMatt Arsenault       runAllDeltaPasses(Tester, SkipPassSet);
221545a8177SArthur Eubanks     } else {
222c3bc72ccSMatt Arsenault       for (StringRef PassName : DeltaPasses) {
223c3bc72ccSMatt Arsenault         if (!SkipPassSet.count(PassName))
224c3bc72ccSMatt Arsenault           runDeltaPassName(Tester, PassName);
225545a8177SArthur Eubanks       }
226545a8177SArthur Eubanks     }
227c3bc72ccSMatt Arsenault 
22835264e71SMatt Arsenault     uint64_t NewComplexity = Tester.getProgram().getComplexityScore();
22935264e71SMatt Arsenault     if (NewComplexity >= OldComplexity)
2304eec1710SJohn Regehr       break;
23135264e71SMatt Arsenault     OldComplexity = NewComplexity;
2324eec1710SJohn Regehr   }
233545a8177SArthur Eubanks }
234