diff options
Diffstat (limited to 'src/qml/compiler')
-rw-r--r-- | src/qml/compiler/qv4codegen.cpp | 45 | ||||
-rw-r--r-- | src/qml/compiler/qv4codegen_p.h | 6 |
2 files changed, 51 insertions, 0 deletions
diff --git a/src/qml/compiler/qv4codegen.cpp b/src/qml/compiler/qv4codegen.cpp index 1bf0e7147d..3c669c9b1a 100644 --- a/src/qml/compiler/qv4codegen.cpp +++ b/src/qml/compiler/qv4codegen.cpp @@ -45,6 +45,8 @@ #include <QtCore/QStack> #include <QScopeGuard> #include <private/qqmljsast_p.h> +#include <private/qqmljslexer_p.h> +#include <private/qqmljsparser_p.h> #include <private/qv4string_p.h> #include <private/qv4value_p.h> #include <private/qv4compilercontext_p.h> @@ -3800,6 +3802,49 @@ QQmlRefPointer<CompiledData::CompilationUnit> Codegen::createUnitForLoading() return result; } +QQmlRefPointer<CompiledData::CompilationUnit> Codegen::compileModule( + bool debugMode, const QString &url, const QString &sourceCode, + const QDateTime &sourceTimeStamp, QList<QQmlJS::DiagnosticMessage> *diagnostics) +{ + QQmlJS::Engine ee; + QQmlJS::Lexer lexer(&ee); + lexer.setCode(sourceCode, /*line*/1, /*qml mode*/false); + QQmlJS::Parser parser(&ee); + + const bool parsed = parser.parseModule(); + + if (diagnostics) + *diagnostics = parser.diagnosticMessages(); + + if (!parsed) + return nullptr; + + QQmlJS::AST::ESModule *moduleNode = QQmlJS::AST::cast<QQmlJS::AST::ESModule*>(parser.rootNode()); + if (!moduleNode) { + // if parsing was successful, and we have no module, then + // the file was empty. + if (diagnostics) + diagnostics->clear(); + return nullptr; + } + + using namespace QV4::Compiler; + Compiler::Module compilerModule(debugMode); + compilerModule.unitFlags |= CompiledData::Unit::IsESModule; + compilerModule.sourceTimeStamp = sourceTimeStamp; + JSUnitGenerator jsGenerator(&compilerModule); + Codegen cg(&jsGenerator, /*strictMode*/true); + cg.generateFromModule(url, url, sourceCode, moduleNode, &compilerModule); + auto errors = cg.errors(); + if (diagnostics) + *diagnostics << errors; + + if (!errors.isEmpty()) + return nullptr; + + return cg.generateCompilationUnit(); +} + class Codegen::VolatileMemoryLocationScanner: protected QQmlJS::AST::Visitor { VolatileMemoryLocations locs; diff --git a/src/qml/compiler/qv4codegen_p.h b/src/qml/compiler/qv4codegen_p.h index ad86483132..ece76e4406 100644 --- a/src/qml/compiler/qv4codegen_p.h +++ b/src/qml/compiler/qv4codegen_p.h @@ -52,6 +52,7 @@ #include "private/qv4global_p.h" #include <private/qqmljsastvisitor_p.h> +#include <private/qqmljsengine_p.h> #include <private/qqmljsast_p.h> #include <private/qv4compiler_p.h> #include <private/qv4compilercontext_p.h> @@ -59,6 +60,8 @@ #include <private/qv4bytecodegenerator_p.h> #include <private/qv4stackframe_p.h> +#include <QtQml/qqmlerror.h> + QT_BEGIN_NAMESPACE using namespace QQmlJS; @@ -683,6 +686,9 @@ public: QQmlRefPointer<QV4::CompiledData::CompilationUnit> generateCompilationUnit(bool generateUnitData = true); static QQmlRefPointer<QV4::CompiledData::CompilationUnit> createUnitForLoading(); + static QQmlRefPointer<CompiledData::CompilationUnit> compileModule( + bool debugMode, const QString &url, const QString &sourceCode, + const QDateTime &sourceTimeStamp, QList<DiagnosticMessage> *diagnostics); Context *currentContext() const { return _context; } BytecodeGenerator *generator() const { return bytecodeGenerator; } |