diff options
author | Olivier Goffart <ogoffart@trolltech.com> | 2009-07-29 16:03:25 (GMT) |
---|---|---|
committer | Olivier Goffart <ogoffart@trolltech.com> | 2009-07-30 12:42:06 (GMT) |
commit | c73ff675063c9dd0266f0c66b821b85d44df3a90 (patch) | |
tree | 09309825827c3ac17a69a84f7395658cda152404 /src | |
parent | 2d1020683ad9aa81ee78e1a5419a3b51d8b36270 (diff) | |
download | Qt-c73ff675063c9dd0266f0c66b821b85d44df3a90.zip Qt-c73ff675063c9dd0266f0c66b821b85d44df3a90.tar.gz Qt-c73ff675063c9dd0266f0c66b821b85d44df3a90.tar.bz2 |
Implement QScriptEngine::pushContext end popContext
Reviewed-by: Kent Hansen
Diffstat (limited to 'src')
-rw-r--r-- | src/script/api/qscriptcontext.cpp | 4 | ||||
-rw-r--r-- | src/script/api/qscriptengine.cpp | 28 |
2 files changed, 28 insertions, 4 deletions
diff --git a/src/script/api/qscriptcontext.cpp b/src/script/api/qscriptcontext.cpp index 0efb037..e820596 100644 --- a/src/script/api/qscriptcontext.cpp +++ b/src/script/api/qscriptcontext.cpp @@ -304,7 +304,9 @@ QScriptEngine *QScriptContext::engine() const QScriptValue QScriptContext::argument(int index) const { Q_D(const QScriptContext); - if ((index < 0) || (index >= argumentCount())) + if (index < 0) + return QScriptValue(); + if (index >= argumentCount()) return QScriptValue(QScriptValue::UndefinedValue); JSC::Register* thisRegister = d->frame->registers() - JSC::RegisterFile::CallFrameHeaderSize - d->frame->argumentCount(); if (d->frame->codeBlock() == 0) diff --git a/src/script/api/qscriptengine.cpp b/src/script/api/qscriptengine.cpp index 0e572af..121658a 100644 --- a/src/script/api/qscriptengine.cpp +++ b/src/script/api/qscriptengine.cpp @@ -78,6 +78,7 @@ #include "bridge/qscriptclassobject_p.h" #include "bridge/qscriptvariant_p.h" #include "bridge/qscriptqobject_p.h" +#include "bridge/qscriptactivationobject_p.h" #ifndef QT_NO_QOBJECT #include <QtCore/qcoreapplication.h> @@ -2285,13 +2286,29 @@ QScriptContext *QScriptEngine::currentContext() const will be local to the context; in other words, the script doesn't have any effect on the global environment. + Returns 0 in case of stack overflow + \sa popContext() */ QScriptContext *QScriptEngine::pushContext() { Q_D(QScriptEngine); - qWarning("QScriptEngine::pushContext() not implemented"); - return d->contextForFrame(d->currentFrame); + const int argCount = 1; // for 'this' + JSC::RegisterFile ®isterFile = d->currentFrame->interpreter()->registerFile(); + JSC::Register *const newEnd = registerFile.end() + JSC::RegisterFile::CallFrameHeaderSize + argCount; + if (!registerFile.grow(newEnd)) + return 0; + + JSC::CallFrame* previousFrame = d->currentFrame; + JSC::JSObject* scope = new (d->currentFrame) QScript::QScriptActivationObject(d->currentFrame); + + d->currentFrame = JSC::CallFrame::create(newEnd); + d->currentFrame->init(0, 0, previousFrame->scopeChain()->copy()->push(scope), + previousFrame, 0, argCount, 0); + QScriptContext *ctx = d->contextForFrame(d->currentFrame); + ctx->setThisObject(globalObject()); + return ctx; + #ifndef Q_SCRIPT_NO_EVENT_NOTIFY // notifyContextPush(); TODO #endif @@ -2306,7 +2323,12 @@ QScriptContext *QScriptEngine::pushContext() void QScriptEngine::popContext() { Q_D(QScriptEngine); - qWarning("QScriptEngine::popContext() not implemented"); + JSC::RegisterFile ®isterFile = d->currentFrame->interpreter()->registerFile(); + JSC::Register *const newEnd = d->currentFrame->registers() - JSC::RegisterFile::CallFrameHeaderSize - d->currentFrame->argumentCount(); + d->currentFrame->scopeChain()->pop()->deref(); + d->releaseContextForFrame(d->currentFrame); + d->currentFrame = d->currentFrame->callerFrame(); + registerFile.shrink(newEnd); #ifndef Q_SCRIPT_NO_EVENT_NOTIFY // notifyContextPop(); TODO #endif |