aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLars Knoll <lars.knoll@qt.io>2018-03-14 15:41:50 +0100
committerLars Knoll <lars.knoll@qt.io>2018-04-26 20:26:45 +0000
commit2ca47e49a25b92e70f6fa6c7a15cb7102a52435c (patch)
tree4800473ad11ba4d239880769e7c304defc1068a1
parent3354628fd9e4c5f2255161a6ca8a5be63ff5bb89 (diff)
Fix some bugs in binding destructuring
Change-Id: I4b18a88e443f3b263cbb1e2b5ca1ebbd353afa98 Reviewed-by: Simon Hausmann <simon.hausmann@qt.io>
-rw-r--r--src/qml/compiler/qv4codegen.cpp12
-rw-r--r--src/qml/compiler/qv4instr_moth.cpp3
-rw-r--r--src/qml/compiler/qv4instr_moth_p.h2
-rw-r--r--src/qml/jit/qv4jit.cpp22
-rw-r--r--src/qml/jit/qv4jit_p.h1
-rw-r--r--src/qml/jsruntime/qv4vme_moth.cpp5
-rw-r--r--tests/auto/qml/ecmascripttests/TestExpectations13
7 files changed, 42 insertions, 16 deletions
diff --git a/src/qml/compiler/qv4codegen.cpp b/src/qml/compiler/qv4codegen.cpp
index f7617c66de..99811c3779 100644
--- a/src/qml/compiler/qv4codegen.cpp
+++ b/src/qml/compiler/qv4codegen.cpp
@@ -421,6 +421,12 @@ void Codegen::initializeAndDestructureBindingElement(AST::BindingElement *e, con
destructureElementList(varToStore, l);
} else if (BindingPropertyList *p = e->propertyList()) {
destructurePropertyList(varToStore, p);
+ } else if (e->name.isNull()) {
+ // empty binding pattern. For spec compatibility, try to coerce the argument to an object
+ varToStore.loadInAccumulator();
+ Instruction::ToObject toObject;
+ bytecodeGenerator->addInstruction(toObject);
+ return;
}
}
@@ -449,10 +455,10 @@ void Codegen::destructureElementList(const Codegen::Reference &array, BindingEle
Reference idx = Reference::fromConst(this, Encode(index));
Reference property = Reference::fromSubscript(array, idx);
- BindingElement *e = p->bindingElement();
- if (e)
+ if (BindingElement *e = p->bindingElement())
initializeAndDestructureBindingElement(e, property);
- else {
+ else if (BindingRestElement *r = p->bindingRestElement()) {
+ Q_UNUSED(r);
throwSyntaxError(bindingList->firstSourceLocation(), QString::fromLatin1("Support for rest elements in binding arrays not implemented!"));
}
}
diff --git a/src/qml/compiler/qv4instr_moth.cpp b/src/qml/compiler/qv4instr_moth.cpp
index 3a9cecdae0..dbdef418a0 100644
--- a/src/qml/compiler/qv4instr_moth.cpp
+++ b/src/qml/compiler/qv4instr_moth.cpp
@@ -461,6 +461,9 @@ void dumpBytecode(const char *code, int len, int nLocals, int nFormals, int /*st
MOTH_BEGIN_INSTR(ConvertThisToObject)
MOTH_END_INSTR(ConvertThisToObject)
+ MOTH_BEGIN_INSTR(ToObject)
+ MOTH_END_INSTR(ToObject)
+
MOTH_BEGIN_INSTR(Construct)
d << "new" << dumpRegister(func, nFormals) << dumpArguments(argc, argv, nFormals);
MOTH_END_INSTR(Construct)
diff --git a/src/qml/compiler/qv4instr_moth_p.h b/src/qml/compiler/qv4instr_moth_p.h
index 8ce72f4942..7047c74803 100644
--- a/src/qml/compiler/qv4instr_moth_p.h
+++ b/src/qml/compiler/qv4instr_moth_p.h
@@ -130,6 +130,7 @@ QT_BEGIN_NAMESPACE
#define INSTR_CreateUnmappedArgumentsObject(op) INSTRUCTION(op, CreateUnmappedArgumentsObject, 0)
#define INSTR_CreateRestParameter(op) INSTRUCTION(op, CreateRestParameter, 1, argIndex)
#define INSTR_ConvertThisToObject(op) INSTRUCTION(op, ConvertThisToObject, 0)
+#define INSTR_ToObject(op) INSTRUCTION(op, ToObject, 0)
#define INSTR_Construct(op) INSTRUCTION(op, Construct, 3, func, argc, argv)
#define INSTR_Jump(op) INSTRUCTION(op, Jump, 1, offset)
#define INSTR_JumpTrue(op) INSTRUCTION(op, JumpTrue, 1, offset)
@@ -248,6 +249,7 @@ QT_BEGIN_NAMESPACE
F(CreateUnmappedArgumentsObject) \
F(CreateRestParameter) \
F(ConvertThisToObject) \
+ F(ToObject) \
F(Construct) \
F(Jump) \
F(JumpTrue) \
diff --git a/src/qml/jit/qv4jit.cpp b/src/qml/jit/qv4jit.cpp
index b2dde4fca2..429d721ba2 100644
--- a/src/qml/jit/qv4jit.cpp
+++ b/src/qml/jit/qv4jit.cpp
@@ -809,6 +809,25 @@ void BaselineJIT::generate_ConvertThisToObject()
as->checkException();
}
+static ReturnedValue ToObjectHelper(ExecutionEngine *engine, const Value &obj)
+{
+ if (obj.isObject())
+ return obj.asReturnedValue();
+
+ return obj.toObject(engine)->asReturnedValue();
+}
+
+void BaselineJIT::generate_ToObject()
+{
+ STORE_ACC();
+ as->prepareCallWithArgCount(2);
+ as->passAccumulatorAsArg(1);
+ as->passEngineAsArg(0);
+ JIT_GENERATE_RUNTIME_CALL(ToObjectHelper, Assembler::ResultInAccumulator);
+ as->checkException();
+
+}
+
void BaselineJIT::generate_Construct(int func, int argc, int argv)
{
STORE_IP();
@@ -1184,6 +1203,9 @@ void BaselineJIT::collectLabelsInBytecode()
MOTH_BEGIN_INSTR(CreateRestParameter)
MOTH_END_INSTR(CreateRestParameter)
+ MOTH_BEGIN_INSTR(ToObject)
+ MOTH_END_INSTR(ToObject)
+
MOTH_BEGIN_INSTR(ConvertThisToObject)
MOTH_END_INSTR(ConvertThisToObject)
diff --git a/src/qml/jit/qv4jit_p.h b/src/qml/jit/qv4jit_p.h
index 9ff2d99191..62866895c4 100644
--- a/src/qml/jit/qv4jit_p.h
+++ b/src/qml/jit/qv4jit_p.h
@@ -194,6 +194,7 @@ public:
void generate_CreateUnmappedArgumentsObject() override;
void generate_CreateRestParameter(int argIndex) override;
void generate_ConvertThisToObject() override;
+ void generate_ToObject() override;
void generate_Construct(int func, int argc, int argv) override;
void generate_Jump(int offset) override;
void generate_JumpTrue(int offset) override;
diff --git a/src/qml/jsruntime/qv4vme_moth.cpp b/src/qml/jsruntime/qv4vme_moth.cpp
index fae917dbb5..a2a602ac58 100644
--- a/src/qml/jsruntime/qv4vme_moth.cpp
+++ b/src/qml/jsruntime/qv4vme_moth.cpp
@@ -997,6 +997,11 @@ QV4::ReturnedValue VME::exec(const FunctionObject *fo, const Value *thisObject,
}
MOTH_END_INSTR(ConvertThisToObject)
+ MOTH_BEGIN_INSTR(ToObject)
+ acc = ACC.toObject(engine)->asReturnedValue();
+ CHECK_EXCEPTION;
+ MOTH_END_INSTR(ToObject)
+
MOTH_BEGIN_INSTR(Construct)
STORE_IP();
acc = Runtime::method_construct(engine, STACK_VALUE(func), stack + argv, argc);
diff --git a/tests/auto/qml/ecmascripttests/TestExpectations b/tests/auto/qml/ecmascripttests/TestExpectations
index e227163fe6..f9c54d099c 100644
--- a/tests/auto/qml/ecmascripttests/TestExpectations
+++ b/tests/auto/qml/ecmascripttests/TestExpectations
@@ -4058,11 +4058,6 @@ language/computed-property-names/to-name-side-effects/class
language/computed-property-names/to-name-side-effects/numbers-class
language/computed-property-names/to-name-side-effects/numbers-object
language/computed-property-names/to-name-side-effects/object
-language/destructuring/binding/initialization-requires-object-coercible-null
-language/destructuring/binding/initialization-requires-object-coercible-undefined
-language/destructuring/binding/syntax/array-elements-with-object-patterns
-language/destructuring/binding/syntax/array-pattern-with-elisions
-language/destructuring/binding/syntax/array-pattern-with-no-elements
language/destructuring/binding/syntax/array-rest-elements
language/destructuring/binding/syntax/recursive-array-and-object-patterns
language/eval-code/direct/lex-env-distinct-cls
@@ -5681,8 +5676,6 @@ language/expressions/function/dstr-dflt-ary-ptrn-rest-id-iter-step-err
language/expressions/function/dstr-dflt-ary-ptrn-rest-id-iter-val-err
language/expressions/function/dstr-dflt-ary-ptrn-rest-obj-id
language/expressions/function/dstr-dflt-ary-ptrn-rest-obj-prop-id
-language/expressions/function/dstr-dflt-obj-init-null
-language/expressions/function/dstr-dflt-obj-init-undefined
language/expressions/function/dstr-dflt-obj-ptrn-id-init-fn-name-arrow
language/expressions/function/dstr-dflt-obj-ptrn-id-init-fn-name-class
language/expressions/function/dstr-dflt-obj-ptrn-id-init-fn-name-cover
@@ -5691,8 +5684,6 @@ language/expressions/function/dstr-dflt-obj-ptrn-id-init-fn-name-gen
language/expressions/function/dstr-dflt-obj-ptrn-prop-ary
language/expressions/function/dstr-dflt-obj-ptrn-prop-ary-init
language/expressions/function/dstr-dflt-obj-ptrn-prop-eval-err
-language/expressions/function/dstr-obj-init-null
-language/expressions/function/dstr-obj-init-undefined
language/expressions/function/dstr-obj-ptrn-id-init-fn-name-arrow
language/expressions/function/dstr-obj-ptrn-id-init-fn-name-class
language/expressions/function/dstr-obj-ptrn-id-init-fn-name-cover
@@ -8912,8 +8903,6 @@ language/statements/function/dstr-dflt-ary-ptrn-rest-id-iter-step-err
language/statements/function/dstr-dflt-ary-ptrn-rest-id-iter-val-err
language/statements/function/dstr-dflt-ary-ptrn-rest-obj-id
language/statements/function/dstr-dflt-ary-ptrn-rest-obj-prop-id
-language/statements/function/dstr-dflt-obj-init-null
-language/statements/function/dstr-dflt-obj-init-undefined
language/statements/function/dstr-dflt-obj-ptrn-id-init-fn-name-arrow
language/statements/function/dstr-dflt-obj-ptrn-id-init-fn-name-class
language/statements/function/dstr-dflt-obj-ptrn-id-init-fn-name-cover
@@ -8922,8 +8911,6 @@ language/statements/function/dstr-dflt-obj-ptrn-id-init-fn-name-gen
language/statements/function/dstr-dflt-obj-ptrn-prop-ary
language/statements/function/dstr-dflt-obj-ptrn-prop-ary-init
language/statements/function/dstr-dflt-obj-ptrn-prop-eval-err
-language/statements/function/dstr-obj-init-null
-language/statements/function/dstr-obj-init-undefined
language/statements/function/dstr-obj-ptrn-id-init-fn-name-arrow
language/statements/function/dstr-obj-ptrn-id-init-fn-name-class
language/statements/function/dstr-obj-ptrn-id-init-fn-name-cover