From 48ea68aa581d492c48fe9e08b54e9ce26f3508b9 Mon Sep 17 00:00:00 2001 From: Andres Noetzli Date: Mon, 1 Oct 2018 10:06:38 -0700 Subject: Refactor preprocessing pass registration (#2468) This commit refactors how preprocessing pass registration works, inspired by LLVM's approach [0]. The basic idea is that every preprocessing pass declares a static variable of type `RegisterPass` in its source file that registers the pass with the `PreprocessingPassRegistry` when starting the program. The registry is a singleton that keeps track of all the available passes and allows other code to create instances of the passes (note: previously the registry itself was owning the passes but this is no longer the case). One of the advantages of this solution is that we have a list of available passes directly at the beginning of the program, which is useful for example when parsing options. As a side effect, this commit also fixes the SortInference pass, which was expecting arguments other than the preprocessing pass context in its constructor. This commit is required for fixing dumping pre/post preprocessing passes. It is also the ground work for allowing the user to specify a preprocessing pipeline using command-line arguments. [0] https://llvm.org/docs/WritingAnLLVMPass.html --- src/preprocessing/preprocessing_pass_registry.cpp | 47 +++++++++++++++-------- 1 file changed, 30 insertions(+), 17 deletions(-) (limited to 'src/preprocessing/preprocessing_pass_registry.cpp') diff --git a/src/preprocessing/preprocessing_pass_registry.cpp b/src/preprocessing/preprocessing_pass_registry.cpp index 03aaec46a..a50cd2541 100644 --- a/src/preprocessing/preprocessing_pass_registry.cpp +++ b/src/preprocessing/preprocessing_pass_registry.cpp @@ -11,11 +11,14 @@ ** ** \brief The preprocessing pass registry ** - ** The preprocessing pass registry. + ** This file defines the classes PreprocessingPassRegistry, which keeps track + ** of the available preprocessing passes, and RegisterPass, which registers a + ** preprocessing pass with the registry. **/ #include "preprocessing/preprocessing_pass_registry.h" +#include #include #include "base/cvc4_assert.h" @@ -25,29 +28,39 @@ namespace CVC4 { namespace preprocessing { -void PreprocessingPassRegistry::registerPass( - const std::string& ppName, - std::unique_ptr preprocessingPass) { - Debug("pp-registry") << "Registering pass " << ppName << std::endl; - Assert(preprocessingPass != nullptr); - Assert(!this->hasPass(ppName)); - d_stringToPreprocessingPass[ppName] = std::move(preprocessingPass); +PreprocessingPassRegistry& PreprocessingPassRegistry::getInstance() +{ + static PreprocessingPassRegistry* ppReg = new PreprocessingPassRegistry(); + return *ppReg; +} + +void PreprocessingPassRegistry::registerPassInfo( + const std::string& name, + std::function ctor) +{ + d_ppInfo[name] = ctor; } -bool PreprocessingPassRegistry::hasPass(const std::string& ppName) { - return d_stringToPreprocessingPass.find(ppName) != - d_stringToPreprocessingPass.end(); +PreprocessingPass* PreprocessingPassRegistry::createPass( + PreprocessingPassContext* ppCtx, const std::string& name) +{ + return d_ppInfo[name](ppCtx); } -PreprocessingPass* PreprocessingPassRegistry::getPass( - const std::string& ppName) { - Assert(this->hasPass(ppName)); - return d_stringToPreprocessingPass[ppName].get(); +std::vector PreprocessingPassRegistry::getAvailablePasses() +{ + std::vector passes; + for (const auto& info : d_ppInfo) + { + passes.push_back(info.first); + } + std::sort(passes.begin(), passes.end()); + return passes; } -void PreprocessingPassRegistry::unregisterPasses() +bool PreprocessingPassRegistry::hasPass(const std::string& name) { - d_stringToPreprocessingPass.clear(); + return d_ppInfo.find(name) != d_ppInfo.end(); } } // namespace preprocessing -- cgit v1.2.3