diff options
author | Stuart Ellis <stuart.ellis@arm.com> | 2021-08-12 11:42:08 +0100 |
---|---|---|
committer | Andrzej Warzynski <andrzej.warzynski@arm.com> | 2021-08-12 11:42:16 +0100 |
commit | f52fc591fa34a8c85577108358b3b36c42b6d364 (patch) | |
tree | 15b3d78f63b9d1a9137ab96a126613223c230356 /flang/lib/FrontendTool | |
parent | 8f359a80e466f221e3b3d93e65587d74f9ba2fda (diff) | |
download | llvm-f52fc591fa34a8c85577108358b3b36c42b6d364.zip llvm-f52fc591fa34a8c85577108358b3b36c42b6d364.tar.gz llvm-f52fc591fa34a8c85577108358b3b36c42b6d364.tar.bz2 |
[flang][driver] Add support for Frontend Plugins
Introducing a plugin API and a simple HelloWorld Plugin example.
This patch adds the `-load` and `-plugin` flags to frontend driver and
the code around using custom frontend actions from within a plugin
shared library object.
It also adds to the Driver-help test to check the help option with the
updated driver flags.
Additionally, the patch creates a plugin-example test to check the
HelloWorld plugin example runs correctly. As part of this, a new CMake
flag (`FLANG_BUILD_EXAMPLES`) is added to allow the example to be built
and for the test to run.
This Plugin API has only been tested on Linux.
Reviewed By: awarzynski
Differential Revision: https://reviews.llvm.org/D106137
Diffstat (limited to 'flang/lib/FrontendTool')
-rw-r--r-- | flang/lib/FrontendTool/ExecuteCompilerInvocation.cpp | 31 |
1 files changed, 31 insertions, 0 deletions
diff --git a/flang/lib/FrontendTool/ExecuteCompilerInvocation.cpp b/flang/lib/FrontendTool/ExecuteCompilerInvocation.cpp index a17b6b5..677f8cd 100644 --- a/flang/lib/FrontendTool/ExecuteCompilerInvocation.cpp +++ b/flang/lib/FrontendTool/ExecuteCompilerInvocation.cpp @@ -13,6 +13,7 @@ #include "flang/Frontend/CompilerInstance.h" #include "flang/Frontend/FrontendActions.h" +#include "flang/Frontend/FrontendPluginRegistry.h" #include "clang/Driver/Options.h" #include "llvm/Option/OptTable.h" #include "llvm/Option/Option.h" @@ -62,6 +63,19 @@ static std::unique_ptr<FrontendAction> CreateFrontendBaseAction( return std::make_unique<GetSymbolsSourcesAction>(); case InitOnly: return std::make_unique<InitOnlyAction>(); + case PluginAction: { + for (const FrontendPluginRegistry::entry &plugin : + FrontendPluginRegistry::entries()) { + if (plugin.getName() == ci.frontendOpts().ActionName) { + std::unique_ptr<PluginParseTreeAction> p(plugin.instantiate()); + return std::move(p); + } + } + unsigned diagID = ci.diagnostics().getCustomDiagID( + clang::DiagnosticsEngine::Error, "unable to find plugin '%0'"); + ci.diagnostics().Report(diagID) << ci.frontendOpts().ActionName; + return nullptr; + } default: break; // TODO: @@ -82,6 +96,7 @@ std::unique_ptr<FrontendAction> CreateFrontendAction(CompilerInstance &ci) { return act; } + bool ExecuteCompilerInvocation(CompilerInstance *flang) { // Honor -help. if (flang->frontendOpts().showHelp) { @@ -99,6 +114,22 @@ bool ExecuteCompilerInvocation(CompilerInstance *flang) { return true; } + // Load any requested plugins. + for (const std::string &Path : flang->frontendOpts().plugins) { + std::string Error; + if (llvm::sys::DynamicLibrary::LoadLibraryPermanently( + Path.c_str(), &Error)) { + unsigned diagID = flang->diagnostics().getCustomDiagID( + clang::DiagnosticsEngine::Error, "unable to load plugin '%0': '%1'"); + flang->diagnostics().Report(diagID) << Path << Error; + } + } + + // If there were errors in processing arguments, don't do anything else. + if (flang->diagnostics().hasErrorOccurred()) { + return false; + } + // Create and execute the frontend action. std::unique_ptr<FrontendAction> act(CreateFrontendAction(*flang)); if (!act) |