Update plugin errors

pull/6/head
A. R. Shajii 2021-11-03 15:04:01 -04:00
parent ddca5263a9
commit 8f827da254
8 changed files with 67 additions and 49 deletions

View File

@ -136,12 +136,15 @@ std::unique_ptr<codon::Compiler> processSource(const std::vector<const char *> &
// load plugins
for (const auto &plugin : plugins) {
std::string errMsg;
if (!compiler->load(plugin, &errMsg)) {
codon::compilationError(errMsg, /*file=*/"", /*line=*/0, /*col=*/0,
/*terminate=*/false);
bool failed = false;
llvm::handleAllErrors(
compiler->load(plugin), [&failed](const codon::error::PluginErrorInfo &e) {
codon::compilationError(e.getMessage(), /*file=*/"", /*line=*/0, /*col=*/0,
/*terminate=*/false);
failed = true;
});
if (failed)
return {};
}
}
bool failed = false;
@ -155,7 +158,7 @@ std::unique_ptr<codon::Compiler> processSource(const std::vector<const char *> &
{
TIME("compile");
compiler->compile();
llvm::cantFail(compiler->compile());
}
return compiler;
}

View File

@ -25,21 +25,23 @@ Compiler::Compiler(const std::string &argv0, bool debug,
llvisitor->setPluginManager(plm.get());
}
bool Compiler::load(const std::string &plugin, std::string *errMsg) {
if (auto *p = plm->load(plugin, errMsg)) {
if (!p->info.stdlibPath.empty()) {
cache->pluginImportPaths.push_back(p->info.stdlibPath);
}
for (auto &kw : p->dsl->getExprKeywords()) {
cache->customExprStmts[kw.keyword] = kw.callback;
}
for (auto &kw : p->dsl->getBlockKeywords()) {
cache->customBlockStmts[kw.keyword] = {kw.hasExpr, kw.callback};
}
p->dsl->addIRPasses(pm.get(), debug);
return true;
llvm::Error Compiler::load(const std::string &plugin) {
auto result = plm->load(plugin);
if (auto err = result.takeError())
return err;
auto *p = *result;
if (!p->info.stdlibPath.empty()) {
cache->pluginImportPaths.push_back(p->info.stdlibPath);
}
return false;
for (auto &kw : p->dsl->getExprKeywords()) {
cache->customExprStmts[kw.keyword] = kw.callback;
}
for (auto &kw : p->dsl->getBlockKeywords()) {
cache->customBlockStmts[kw.keyword] = {kw.hasExpr, kw.callback};
}
p->dsl->addIRPasses(pm.get(), debug);
return llvm::Error::success();
}
llvm::Error
@ -95,9 +97,10 @@ Compiler::parseCode(const std::string &file, const std::string &code, int startL
return parse(/*isCode=*/true, file, code, startLine, testFlags, defines);
}
void Compiler::compile() {
llvm::Error Compiler::compile() {
pm->run(module.get());
llvisitor->visit(module.get());
return llvm::Error::success();
}
llvm::Expected<std::string> Compiler::docgen(const std::vector<std::string> &files) {

View File

@ -40,7 +40,7 @@ public:
ir::transform::PassManager *getPassManager() const { return pm.get(); }
ir::LLVMVisitor *getLLVMVisitor() const { return llvisitor.get(); }
bool load(const std::string &plugin, std::string *errMsg);
llvm::Error load(const std::string &plugin);
llvm::Error
parseFile(const std::string &file, int testFlags = 0,
const std::unordered_map<std::string, std::string> &defines = {});
@ -48,7 +48,7 @@ public:
parseCode(const std::string &file, const std::string &code, int startLine = 0,
int testFlags = 0,
const std::unordered_map<std::string, std::string> &defines = {});
void compile();
llvm::Error compile();
llvm::Expected<std::string> docgen(const std::vector<std::string> &files);
};

View File

@ -7,5 +7,7 @@ char ParserErrorInfo::ID = 0;
char RuntimeErrorInfo::ID = 0;
char PluginErrorInfo::ID = 0;
} // namespace error
} // namespace codon

View File

@ -104,5 +104,23 @@ public:
static char ID;
};
class PluginErrorInfo : public llvm::ErrorInfo<PluginErrorInfo> {
private:
std::string message;
public:
explicit PluginErrorInfo(const std::string &message) : message(message) {}
std::string getMessage() const { return message; }
void log(llvm::raw_ostream &out) const override { out << message; }
std::error_code convertToErrorCode() const override {
return llvm::inconvertibleErrorCode();
}
static char ID;
};
} // namespace error
} // namespace codon

View File

@ -10,10 +10,8 @@
namespace codon {
namespace {
Plugin *error(const std::string &msg, std::string *errMsg) {
if (!msg.empty() && errMsg)
*errMsg = msg;
return nullptr;
llvm::Expected<Plugin *> pluginError(const std::string &msg) {
return llvm::make_error<error::PluginErrorInfo>(msg);
}
typedef std::unique_ptr<DSL> LoadFunc();
@ -21,7 +19,7 @@ typedef std::unique_ptr<DSL> LoadFunc();
namespace fs = std::filesystem;
Plugin *PluginManager::load(const std::string &path, std::string *errMsg) {
llvm::Expected<Plugin *> PluginManager::load(const std::string &path) {
#if __APPLE__
const std::string libExt = "dylib";
#else
@ -40,9 +38,8 @@ Plugin *PluginManager::load(const std::string &path, std::string *errMsg) {
try {
tml = toml::parse_file(tomlPath.string());
} catch (const toml::parse_error &e) {
return error(
fmt::format("[toml::parse_file(\"{}\")] {}", tomlPath.string(), e.what()),
errMsg);
return pluginError(
fmt::format("[toml::parse_file(\"{}\")] {}", tomlPath.string(), e.what()));
}
auto about = tml["about"];
auto library = tml["library"];
@ -70,31 +67,26 @@ Plugin *PluginManager::load(const std::string &path, std::string *errMsg) {
semver::version(CODON_VERSION_MAJOR, CODON_VERSION_MINOR, CODON_VERSION_PATCH),
info.supported);
} catch (const std::invalid_argument &e) {
return error(fmt::format("[semver::range::satisfies(..., \"{}\")] {}",
info.supported, e.what()),
errMsg);
return pluginError(fmt::format("[semver::range::satisfies(..., \"{}\")] {}",
info.supported, e.what()));
}
if (!versionOk)
return error(fmt::format("unsupported version {} (supported: {})", CODON_VERSION,
info.supported),
errMsg);
return pluginError(fmt::format("unsupported version {} (supported: {})",
CODON_VERSION, info.supported));
if (!dylibPath.empty()) {
std::string libLoadErrorMsg;
auto handle = llvm::sys::DynamicLibrary::getPermanentLibrary(dylibPath.c_str(),
&libLoadErrorMsg);
if (!handle.isValid())
return error(
fmt::format(
"[llvm::sys::DynamicLibrary::getPermanentLibrary(\"{}\", ...)] {}",
dylibPath, libLoadErrorMsg),
errMsg);
return pluginError(fmt::format(
"[llvm::sys::DynamicLibrary::getPermanentLibrary(\"{}\", ...)] {}", dylibPath,
libLoadErrorMsg));
auto *entry = (LoadFunc *)handle.getAddressOfSymbol("load");
if (!entry)
return error(
fmt::format("could not find 'load' in plugin shared library: {}", dylibPath),
errMsg);
return pluginError(
fmt::format("could not find 'load' in plugin shared library: {}", dylibPath));
auto dsl = (*entry)();
plugins.push_back(std::make_unique<Plugin>(std::move(dsl), info, handle));

View File

@ -5,6 +5,7 @@
#include <string>
#include <vector>
#include "codon/compiler/error.h"
#include "codon/dsl/dsl.h"
#include "codon/sir/util/iterators.h"
#include "llvm/Support/DynamicLibrary.h"
@ -45,9 +46,8 @@ public:
/// Loads the plugin at the given load path.
/// @param path path to plugin directory containing "plugin.toml" file
/// @param errMsg where to store potential error messages, if non-null
/// @return plugin pointer if successful, null otherwise
Plugin *load(const std::string &path, std::string *errMsg = nullptr);
/// @return plugin pointer if successful, plugin error otherwise
llvm::Expected<Plugin *> load(const std::string &path);
};
} // namespace codon

View File

@ -201,7 +201,7 @@ public:
pm->registerPass(std::make_unique<TestOutliner>());
pm->registerPass(std::make_unique<TestInliner>());
compiler->compile();
llvm::cantFail(compiler->compile());
compiler->getLLVMVisitor()->run({file});
fflush(stdout);
exit(EXIT_SUCCESS);