aboutsummaryrefslogtreecommitdiffstats
path: root/qmljs_environment.cpp
diff options
context:
space:
mode:
authorLars Knoll <lars.knoll@digia.com>2012-12-17 13:34:39 +0100
committerSimon Hausmann <simon.hausmann@digia.com>2012-12-17 20:24:20 +0100
commit2d4daa564719d61191aa4907494e8a728fbe335b (patch)
treea8e89549b776fa591c7d54b9354e6fc985cfe49f /qmljs_environment.cpp
parent344a5b804cc9570ebe51f62ff492d3a896d97856 (diff)
Resolve argument names from right to left
Duplicated names for arguments are allowed in JS, later ones shadow previous ones. So we need to iterate from back to front to resolve the names correctly. Change-Id: If427ce9d11ac561457c24e41f79c11263fa0a8dc Reviewed-by: Simon Hausmann <simon.hausmann@digia.com>
Diffstat (limited to 'qmljs_environment.cpp')
-rw-r--r--qmljs_environment.cpp42
1 files changed, 22 insertions, 20 deletions
diff --git a/qmljs_environment.cpp b/qmljs_environment.cpp
index 229d3504ef..d8f4320ca6 100644
--- a/qmljs_environment.cpp
+++ b/qmljs_environment.cpp
@@ -115,18 +115,19 @@ void ExecutionContext::createMutableBinding(String *name, bool deletable)
bool ExecutionContext::setMutableBinding(ExecutionContext *scope, String *name, Value value)
{
// ### throw if scope->strict is true, and it would change an immutable binding
- for (unsigned int i = 0; i < variableCount(); ++i) {
- if (variables()[i]->isEqualTo(name)) {
- locals[i] = value;
- return true;
- }
- }
- for (unsigned int i = 0; i < formalCount(); ++i) {
- if (formals()[i]->isEqualTo(name)) {
- arguments[i] = value;
- return true;
- }
+ if (function) {
+ for (unsigned int i = 0; i < function->varCount; ++i)
+ if (function->varList[i]->isEqualTo(name)) {
+ locals[i] = value;
+ return true;
+ }
+ for (int i = (int)function->formalParameterCount - 1; i >= 0; --i)
+ if (function->formalParameterList[i]->isEqualTo(name)) {
+ arguments[i] = value;
+ return true;
+ }
}
+
if (activation && activation->__hasProperty__(scope, name)) {
activation->__put__(scope, name, value);
return true;
@@ -140,14 +141,15 @@ Value ExecutionContext::getBindingValue(ExecutionContext *scope, String *name, b
Q_UNUSED(strict);
assert(function);
- for (unsigned int i = 0; i < variableCount(); ++i) {
- if (variables()[i]->isEqualTo(name))
- return locals[i];
- }
- for (unsigned int i = 0; i < formalCount(); ++i) {
- if (formals()[i]->isEqualTo(name))
- return arguments[i];
+ if (function) {
+ for (unsigned int i = 0; i < function->varCount; ++i)
+ if (function->varList[i]->isEqualTo(name))
+ return locals[i];
+ for (int i = (int)function->formalParameterCount - 1; i >= 0; --i)
+ if (function->formalParameterList[i]->isEqualTo(name))
+ return arguments[i];
}
+
if (activation) {
bool hasProperty = false;
Value v = activation->__get__(scope, name, &hasProperty);
@@ -288,7 +290,7 @@ Value ExecutionContext::getProperty(String *name)
for (unsigned int i = 0; i < f->varCount; ++i)
if (f->varList[i]->isEqualTo(name))
return ctx->locals[i];
- for (unsigned int i = 0; i < f->formalParameterCount; ++i)
+ for (int i = (int)f->formalParameterCount - 1; i >= 0; --i)
if (f->formalParameterList[i]->isEqualTo(name))
return ctx->arguments[i];
}
@@ -325,7 +327,7 @@ Value ExecutionContext::getPropertyNoThrow(String *name)
for (unsigned int i = 0; i < f->varCount; ++i)
if (f->varList[i]->isEqualTo(name))
return ctx->locals[i];
- for (unsigned int i = 0; i < f->formalParameterCount; ++i)
+ for (int i = (int)f->formalParameterCount - 1; i >= 0; --i)
if (f->formalParameterList[i]->isEqualTo(name))
return ctx->arguments[i];
}