Fix Array.prototype.concat
authorPeter Varga <pvarga@inf.u-szeged.hu>
Tue, 13 Aug 2013 08:43:15 +0000 (10:43 +0200)
committerThe Qt Project <gerrit-noreply@qt-project.org>
Wed, 14 Aug 2013 19:12:06 +0000 (21:12 +0200)
The following tests failed in the test262 test suite due to incomplete
implementation:
- ch15/15.4/15.4.4/15.4.4.4/15.4.4.4-5-c-i-1
- ch15/15.4/15.4.4/15.4.4.4/S15.4.4.4_A2_T1
- ch15/15.4/15.4.4/15.4.4.4/S15.4.4.4_A2_T2
- ch15/15.4/15.4.4/15.4.4.4/S15.4.4.4_A3_T1

Change-Id: I423e77fe3d34140a08c61efdc18c81ef251bc927
Reviewed-by: Lars Knoll <lars.knoll@digia.com>
src/qml/jsruntime/qv4arrayobject.cpp
src/qml/jsruntime/qv4object.cpp
tests/manual/v4/TestExpectations

index b1f2517..214ec93 100644 (file)
@@ -147,9 +147,12 @@ Value ArrayPrototype::method_concat(SimpleCallContext *ctx)
 
     if (ArrayObject *instance = ctx->thisObject.asArrayObject()) {
         result->copyArrayData(instance);
-    } else {
+    } else if (ctx->thisObject.asStringObject()) {
         QString v = ctx->thisObject.toString(ctx)->toQString();
         result->arraySet(0, Value::fromString(ctx, v));
+    } else {
+        Object *instance = ctx->thisObject.asObject();
+        result->arraySet(0, ctx->thisObject);
     }
 
     for (uint i = 0; i < ctx->argumentCount; ++i) {
index ad18edd..6d4b601 100644 (file)
@@ -1065,16 +1065,49 @@ bool Object::__defineOwnProperty__(ExecutionContext *ctx, const QString &name, c
 
 void Object::copyArrayData(Object *other)
 {
-    arrayReserve(other->arrayDataLen);
-    arrayDataLen = other->arrayDataLen;
-    memcpy(arrayData, other->arrayData, arrayDataLen*sizeof(Property));
+    Q_ASSERT(isArrayObject());
+
+    bool protoHasArray = false;
+    Object *p = other;
+    while ((p = p->prototype))
+        if (p->arrayDataLen)
+            protoHasArray = true;
+
+    bool arrayHasGetter = false;
+    if (!protoHasArray && other->arrayAttributes) {
+        for (uint i = 0; i < other->arrayDataLen; ++i) {
+            if (other->arrayAttributes[i].isAccessor()) {
+                const Property &pd = other->arrayData[i];
+                FunctionObject *getter = pd.getter();
+                if (getter) {
+                    arrayHasGetter = true;
+                    break;
+                }
+            }
+        }
+    }
+
+    if (protoHasArray || arrayHasGetter) {
+        uint len = other->arrayLength();
+        Q_ASSERT(len);
+
+        for (uint i = 0; i < len; ++i) {
+            arraySet(i, other->getIndexed(i));
+        }
+    } else {
+        arrayReserve(other->arrayDataLen);
+        arrayDataLen = other->arrayDataLen;
+        memcpy(arrayData, other->arrayData, arrayDataLen*sizeof(Property));
+    }
+
     arrayOffset = 0;
+
     if (other->sparseArray) {
         sparseArray = new SparseArray(*other->sparseArray);
         arrayFreeList = other->arrayFreeList;
     }
-    if (isArrayObject())
-        setArrayLengthUnchecked(other->arrayLength());
+
+    setArrayLengthUnchecked(other->arrayLength());
 }
 
 
index 17cdc3b..8af4842 100644 (file)
@@ -11,9 +11,5 @@ S13_A15_T4 failing
 S13.2.3_A1 failing
 S15.4.4.3_A1_T1 failing
 S15.4.4.3_A3_T1 failing
-15.4.4.4-5-c-i-1 failing
-S15.4.4.4_A2_T1 failing
-S15.4.4.4_A2_T2 failing
-S15.4.4.4_A3_T1 failing
 S15.5.4.11_A5_T1 failing
-S15.2.4.4_A14 failing
\ No newline at end of file
+S15.2.4.4_A14 failing