History

Improve script engine error logging + some cleanup

Atlante45 committed 11 years ago

Commit 421d9671 parent 4e33aa83 files · +56 −25Browse files

Showing the changes to libraries/script-engine/src/ScriptEngine.cpp (1 of 3 files). Show all

Unified · Split

libraries/script-engine/src/ScriptEngine.cpp+51−23
@@ -556,7 +556,7 @@ void ScriptEngine::addEventHandler(const EntityItemID& entityID, const QString& · 555 unmodified lines
556}556}
557 557
558 558
559QScriptValue ScriptEngine::evaluate(const QString& program, const QString& fileName, int lineNumber) {559QScriptValue ScriptEngine::evaluate(const QString& sourceCode, const QString& fileName, int lineNumber) {
560 if (_stoppingAllScripts) {560 if (_stoppingAllScripts) {
561 return QScriptValue(); // bail early561 return QScriptValue(); // bail early
562 }562 }
@@ -565,27 +565,30 @@ QScriptValue ScriptEngine::evaluate(const QString& program, const QString& fileN · 2 unmodified lines
565 QScriptValue result;565 QScriptValue result;
566 #ifdef THREAD_DEBUGGING566 #ifdef THREAD_DEBUGGING
567 qDebug() << "*** WARNING *** ScriptEngine::evaluate() called on wrong thread [" << QThread::currentThread() << "], invoking on correct thread [" << thread() << "] "567 qDebug() << "*** WARNING *** ScriptEngine::evaluate() called on wrong thread [" << QThread::currentThread() << "], invoking on correct thread [" << thread() << "] "
568 "program:" << program << " fileName:" << fileName << "lineNumber:" << lineNumber;568 "sourceCode:" << sourceCode << " fileName:" << fileName << "lineNumber:" << lineNumber;
569 #endif569 #endif
570 QMetaObject::invokeMethod(this, "evaluate", Qt::BlockingQueuedConnection,570 QMetaObject::invokeMethod(this, "evaluate", Qt::BlockingQueuedConnection,
571 Q_RETURN_ARG(QScriptValue, result),571 Q_RETURN_ARG(QScriptValue, result),
572 Q_ARG(const QString&, program),572 Q_ARG(const QString&, sourceCode),
573 Q_ARG(const QString&, fileName),573 Q_ARG(const QString&, fileName),
574 Q_ARG(int, lineNumber));574 Q_ARG(int, lineNumber));
575 return result;575 return result;
576 }576 }
577 577
578 _evaluatesPending++;578 // Check synthax
579 QScriptValue result = QScriptEngine::evaluate(program, fileName, lineNumber);579 const QScriptProgram program(sourceCode, fileName, lineNumber);
580 if (hasUncaughtException()) {580 if (!checkSynthax(program)) {
581 int line = uncaughtExceptionLineNumber();581 return QScriptValue();
582 qCDebug(scriptengine) << "Uncaught exception at (" << _fileNameString << " : " << fileName << ") line" << line << ": " << result.toString();
583 }582 }
584 _evaluatesPending--;583
584 ++_evaluatesPending;
585 const auto result = QScriptEngine::evaluate(program);
586 --_evaluatesPending;
587
588 const auto hadUncaughtException = checkExceptions(this, program.fileName());
585 if (_wantSignals) {589 if (_wantSignals) {
586 emit evaluationFinished(result, hasUncaughtException());590 emit evaluationFinished(result, hadUncaughtException);
587 }591 }
588 clearExceptions();
589 return result;592 return result;
590}593}
591 594
@@ -603,7 +606,7 @@ void ScriptEngine::run() { · 11 unmodified lines
603 emit runningStateChanged();606 emit runningStateChanged();
604 }607 }
605 608
606 QScriptValue result = evaluate(_scriptContents);609 QScriptValue result = evaluate(_scriptContents, _fileNameString);
607 610
608 QElapsedTimer startTime;611 QElapsedTimer startTime;
609 startTime.start();612 startTime.start();
@@ -644,15 +647,6 @@ void ScriptEngine::run() { · 34 unmodified lines
644 qint64 now = usecTimestampNow();647 qint64 now = usecTimestampNow();
645 float deltaTime = (float) (now - lastUpdate) / (float) USECS_PER_SECOND;648 float deltaTime = (float) (now - lastUpdate) / (float) USECS_PER_SECOND;
646 649
647 if (hasUncaughtException()) {
648 int line = uncaughtExceptionLineNumber();
649 qCDebug(scriptengine) << "Uncaught exception at (" << _fileNameString << ") line" << line << ":" << uncaughtException().toString();
650 if (_wantSignals) {
651 emit errorMessage("Uncaught exception at (" + _fileNameString + ") line" + QString::number(line) + ":" + uncaughtException().toString());
652 }
653 clearExceptions();
654 }
655
656 if (!_isFinished) {650 if (!_isFinished) {
657 if (_wantSignals) {651 if (_wantSignals) {
658 emit update(deltaTime);652 emit update(deltaTime);
@@ -660,6 +654,7 @@ void ScriptEngine::run() { · 1 unmodified line
660 }654 }
661 lastUpdate = now;655 lastUpdate = now;
662 656
657 checkExceptions(this, _fileNameString);
663 }658 }
664 659
665 stopAllTimers(); // make sure all our timers are stopped if the script is ending660 stopAllTimers(); // make sure all our timers are stopped if the script is ending
@@ -896,6 +891,38 @@ void ScriptEngine::load(const QString& loadFile) { · 230 unmodified lines
896 }891 }
897}892}
898 893
894
895bool ScriptEngine::checkSynthax(const QScriptProgram& program) {
896 const auto syntaxCheck = QScriptEngine::checkSyntax(program.sourceCode());
897 if (syntaxCheck.state() != QScriptSyntaxCheckResult::Valid) {
898 const auto error = syntaxCheck.errorMessage();
899 const auto line = QString::number(syntaxCheck.errorLineNumber());
900 const auto column = QString::number(syntaxCheck.errorColumnNumber());
901 const auto message = QString("[SyntaxError] %1 in %2:%3(%4)").arg(error, program.fileName(), line, column);
902 qCWarning(scriptengine) << qPrintable(message);
903 return false;
904 }
905 return true;
906}
907
908bool ScriptEngine::checkExceptions(QScriptEngine* engine, const QString& fileName) {
909 if (engine->hasUncaughtException()) {
910 const auto backtrace = engine->uncaughtExceptionBacktrace();
911 const auto exception = engine->uncaughtException().toString();
912 const auto line = QString::number(engine->uncaughtExceptionLineNumber());
913 engine->clearExceptions();
914
915 auto message = QString("[UncaughtException] %1 in %2:%3").arg(exception, fileName, line);
916 if (!backtrace.empty()) {
917 static const auto lineSeparator = "\n ";
918 message += QString("\n[Backtrace]%1%2").arg(lineSeparator, backtrace.join(lineSeparator));
919 }
920 qCWarning(scriptengine) << qPrintable(message);
921 return false;
922 }
923 return true;
924}
925
899// Look up the handler associated with eventName and entityID. If found, evalute the argGenerator thunk and call the handler with those args926// Look up the handler associated with eventName and entityID. If found, evalute the argGenerator thunk and call the handler with those args
900void ScriptEngine::forwardHandlerCall(const EntityItemID& entityID, const QString& eventName, QScriptValueList eventHanderArgs) {927void ScriptEngine::forwardHandlerCall(const EntityItemID& entityID, const QString& eventName, QScriptValueList eventHanderArgs) {
901 if (QThread::currentThread() != thread()) {928 if (QThread::currentThread() != thread()) {
@@ -1015,7 +1042,8 @@ void ScriptEngine::entityScriptContentAvailable(const EntityItemID& entityID, co · 113 unmodified lines
1015 lastModified = (quint64)QFileInfo(file).lastModified().toMSecsSinceEpoch();1042 lastModified = (quint64)QFileInfo(file).lastModified().toMSecsSinceEpoch();
1016 }1043 }
1017 1044
1018 QScriptValue entityScriptConstructor = evaluate(contents);1045 auto fileName = QString("(EntityID:%1, %2)").arg(entityID.toString(), isURL ? scriptOrURL : "EmbededEntityScript");
1046 QScriptValue entityScriptConstructor = evaluate(contents, fileName);
1019 QScriptValue entityScriptObject = entityScriptConstructor.construct();1047 QScriptValue entityScriptObject = entityScriptConstructor.construct();
1020 EntityScriptDetails newDetails = { scriptOrURL, entityScriptObject, lastModified };1048 EntityScriptDetails newDetails = { scriptOrURL, entityScriptObject, lastModified };
1021 _entityScripts[entityID] = newDetails;1049 _entityScripts[entityID] = newDetails;