Don't call generator when declarations already deleted
This commit is contained in:
parent
31c37a8ee4
commit
fe40840486
|
@ -66,20 +66,7 @@ void CodeFactory::addDeclaration(clang::Decl *decl)
|
||||||
}
|
}
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief Reads (relevent) AST elements using Clang.
|
* \brief Generates code based on the added declarations.
|
||||||
*/
|
|
||||||
bool CodeFactory::readAST()
|
|
||||||
{
|
|
||||||
// lazy initialize Clang tool invocation
|
|
||||||
if (!m_toolInvocation) {
|
|
||||||
m_toolInvocation = make_unique<ToolInvocation>(*this);
|
|
||||||
}
|
|
||||||
// run Clang
|
|
||||||
return m_toolInvocation->invocation.run();
|
|
||||||
}
|
|
||||||
|
|
||||||
/*!
|
|
||||||
* \brief Generates code based on the AST elements which have been read by invoking readAST().
|
|
||||||
*/
|
*/
|
||||||
bool CodeFactory::generate() const
|
bool CodeFactory::generate() const
|
||||||
{
|
{
|
||||||
|
@ -89,4 +76,17 @@ bool CodeFactory::generate() const
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*!
|
||||||
|
* \brief Reads (relevent) AST elements using Clang and generates code.
|
||||||
|
*/
|
||||||
|
bool CodeFactory::run()
|
||||||
|
{
|
||||||
|
// lazy initialize Clang tool invocation
|
||||||
|
if (!m_toolInvocation) {
|
||||||
|
m_toolInvocation = make_unique<ToolInvocation>(*this);
|
||||||
|
}
|
||||||
|
// run Clang
|
||||||
|
return m_toolInvocation->invocation.run();
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace ReflectiveRapidJSON
|
} // namespace ReflectiveRapidJSON
|
||||||
|
|
|
@ -14,6 +14,9 @@ class CompilerInstance;
|
||||||
|
|
||||||
namespace ReflectiveRapidJSON {
|
namespace ReflectiveRapidJSON {
|
||||||
|
|
||||||
|
class Consumer;
|
||||||
|
class Visitor;
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief The CodeFactory class produces additional (reflection) code for a specified list of C++ source files.
|
* \brief The CodeFactory class produces additional (reflection) code for a specified list of C++ source files.
|
||||||
* \remarks
|
* \remarks
|
||||||
|
@ -21,6 +24,9 @@ namespace ReflectiveRapidJSON {
|
||||||
* - The CodeFactory class is constituted by its underlying CodeGenerator instances.
|
* - The CodeFactory class is constituted by its underlying CodeGenerator instances.
|
||||||
*/
|
*/
|
||||||
class CodeFactory {
|
class CodeFactory {
|
||||||
|
friend class Consumer;
|
||||||
|
friend class Visitor;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
CodeFactory(
|
CodeFactory(
|
||||||
const char *applicationPath, const std::vector<const char *> &sourceFiles, const std::vector<const char *> &clangOptions, std::ostream &os);
|
const char *applicationPath, const std::vector<const char *> &sourceFiles, const std::vector<const char *> &clangOptions, std::ostream &os);
|
||||||
|
@ -29,15 +35,15 @@ public:
|
||||||
const std::vector<std::unique_ptr<CodeGenerator>> &generators() const;
|
const std::vector<std::unique_ptr<CodeGenerator>> &generators() const;
|
||||||
template <typename GeneratorType> void addGenerator();
|
template <typename GeneratorType> void addGenerator();
|
||||||
|
|
||||||
void addDeclaration(clang::Decl *decl);
|
bool run();
|
||||||
bool readAST();
|
|
||||||
bool generate() const;
|
|
||||||
clang::CompilerInstance *compilerInstance();
|
clang::CompilerInstance *compilerInstance();
|
||||||
void setCompilerInstance(clang::CompilerInstance *compilerInstance);
|
void setCompilerInstance(clang::CompilerInstance *compilerInstance);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
struct ToolInvocation;
|
struct ToolInvocation;
|
||||||
|
|
||||||
|
void addDeclaration(clang::Decl *decl);
|
||||||
|
bool generate() const;
|
||||||
std::vector<std::string> makeClangArgs() const;
|
std::vector<std::string> makeClangArgs() const;
|
||||||
|
|
||||||
const char *const m_applicationPath;
|
const char *const m_applicationPath;
|
||||||
|
|
|
@ -123,7 +123,7 @@ std::vector<const JSONSerializationCodeGenerator::RelevantClass *> JSONSerializa
|
||||||
{
|
{
|
||||||
vector<const RelevantClass *> relevantBaseClasses;
|
vector<const RelevantClass *> relevantBaseClasses;
|
||||||
for (const RelevantClass &otherClass : m_relevantClasses) {
|
for (const RelevantClass &otherClass : m_relevantClasses) {
|
||||||
if (relevantClass.record->isDerivedFrom(otherClass.record)) {
|
if (relevantClass.record != otherClass.record && relevantClass.record->isDerivedFrom(otherClass.record)) {
|
||||||
relevantBaseClasses.push_back(&otherClass);
|
relevantBaseClasses.push_back(&otherClass);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
#include "./consumer.h"
|
#include "./consumer.h"
|
||||||
|
#include "./codefactory.h"
|
||||||
|
|
||||||
#include <clang/AST/ASTContext.h>
|
#include <clang/AST/ASTContext.h>
|
||||||
#include <clang/AST/DeclCXX.h>
|
#include <clang/AST/DeclCXX.h>
|
||||||
|
@ -29,6 +30,12 @@ bool Consumer::HandleTopLevelDecl(clang::DeclGroupRef groupRefDecl)
|
||||||
return clang::ASTConsumer::HandleTopLevelDecl(groupRefDecl);
|
return clang::ASTConsumer::HandleTopLevelDecl(groupRefDecl);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Consumer::HandleTranslationUnit(clang::ASTContext &context)
|
||||||
|
{
|
||||||
|
m_visitor.TraverseDecl(context.getTranslationUnitDecl());
|
||||||
|
m_factory.generate();
|
||||||
|
}
|
||||||
|
|
||||||
void DiagConsumer::BeginSourceFile(const clang::LangOptions &langOpts, const clang::Preprocessor *pp)
|
void DiagConsumer::BeginSourceFile(const clang::LangOptions &langOpts, const clang::Preprocessor *pp)
|
||||||
{
|
{
|
||||||
m_proxy->BeginSourceFile(langOpts, pp);
|
m_proxy->BeginSourceFile(langOpts, pp);
|
||||||
|
|
|
@ -44,11 +44,6 @@ inline Consumer::Consumer(CodeFactory &factory, clang::CompilerInstance &compile
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void Consumer::HandleTranslationUnit(clang::ASTContext &context)
|
|
||||||
{
|
|
||||||
m_visitor.TraverseDecl(context.getTranslationUnitDecl());
|
|
||||||
}
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief The DiagConsumer class changes most errors into warnings.
|
* \brief The DiagConsumer class changes most errors into warnings.
|
||||||
* \remarks This class is based on MocDiagConsumer from https://github.com/woboq/moc-ng.
|
* \remarks This class is based on MocDiagConsumer from https://github.com/woboq/moc-ng.
|
||||||
|
|
|
@ -77,18 +77,12 @@ int main(int argc, char *argv[])
|
||||||
factory.addGenerator<JSONSerializationCodeGenerator>();
|
factory.addGenerator<JSONSerializationCodeGenerator>();
|
||||||
}
|
}
|
||||||
|
|
||||||
// read AST elements from input files
|
// read AST elements from input files and run the code generator
|
||||||
if (!factory.readAST()) {
|
if (!factory.run()) {
|
||||||
cerr << Phrases::Error << "Errors occured when parsing the input file." << Phrases::EndFlush;
|
cerr << Phrases::Error << "Errors occured." << Phrases::EndFlush;
|
||||||
return -2;
|
return -2;
|
||||||
}
|
}
|
||||||
|
|
||||||
// run the code generator
|
|
||||||
if (!factory.generate()) {
|
|
||||||
cerr << Phrases::Error << "Errors occured when during code generation." << Phrases::EndFlush;
|
|
||||||
return -3;
|
|
||||||
}
|
|
||||||
|
|
||||||
} catch (...) {
|
} catch (...) {
|
||||||
catchIoFailure();
|
catchIoFailure();
|
||||||
const char *errorMessage;
|
const char *errorMessage;
|
||||||
|
|
Loading…
Reference in New Issue