Jacek Caban : jscript: Added Array.prototype.indexOf implementation.

Alexandre Julliard julliard at winehq.org
Fri Mar 2 12:16:45 CST 2018


Module: wine
Branch: master
Commit: 3987d939920ee8b60282200d4f327ccd17c34aa5
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=3987d939920ee8b60282200d4f327ccd17c34aa5

Author: Jacek Caban <jacek at codeweavers.com>
Date:   Thu Mar  1 23:58:55 2018 +0100

jscript: Added Array.prototype.indexOf implementation.

Signed-off-by: Jacek Caban <jacek at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 dlls/jscript/array.c              | 57 +++++++++++++++++++++++++++++++++++++++
 dlls/jscript/engine.c             |  2 +-
 dlls/jscript/jscript.h            |  2 ++
 dlls/mshtml/tests/documentmode.js |  1 +
 dlls/mshtml/tests/es5.js          | 29 ++++++++++++++++++++
 5 files changed, 90 insertions(+), 1 deletion(-)

diff --git a/dlls/jscript/array.c b/dlls/jscript/array.c
index 90ff313..9c287c9 100644
--- a/dlls/jscript/array.c
+++ b/dlls/jscript/array.c
@@ -47,6 +47,7 @@ static const WCHAR spliceW[] = {'s','p','l','i','c','e',0};
 static const WCHAR toStringW[] = {'t','o','S','t','r','i','n','g',0};
 static const WCHAR toLocaleStringW[] = {'t','o','L','o','c','a','l','e','S','t','r','i','n','g',0};
 static const WCHAR unshiftW[] = {'u','n','s','h','i','f','t',0};
+static const WCHAR indexOfW[] = {'i','n','d','e','x','O','f',0};
 
 static const WCHAR default_separatorW[] = {',',0};
 
@@ -946,6 +947,61 @@ static HRESULT Array_toLocaleString(script_ctx_t *ctx, vdisp_t *vthis, WORD flag
     return E_NOTIMPL;
 }
 
+static HRESULT Array_indexOf(script_ctx_t *ctx, vdisp_t *vthis, WORD flags, unsigned argc, jsval_t *argv,
+        jsval_t *r)
+{
+    jsdisp_t *jsthis;
+    unsigned length, i, from = 0;
+    jsval_t search, value;
+    BOOL eq;
+    HRESULT hres;
+
+    TRACE("\n");
+
+    hres = get_length(ctx, vthis, &jsthis, &length);
+    if(FAILED(hres))
+        return hres;
+    if(!length) {
+        if(r) *r = jsval_number(-1);
+        return S_OK;
+    }
+
+    search = argc ? argv[0] : jsval_undefined();
+
+    if(argc > 1) {
+        double from_arg;
+
+        hres = to_integer(ctx, argv[1], &from_arg);
+        if(FAILED(hres))
+            return hres;
+
+        if(from_arg >= 0)
+            from = min(from_arg, length);
+        else
+            from = max(from_arg + length, 0);
+    }
+
+    for(i = from; i < length; i++) {
+        hres = jsdisp_get_idx(jsthis, i, &value);
+        if(hres == DISP_E_UNKNOWNNAME)
+            continue;
+        if(FAILED(hres))
+            return hres;
+
+        hres = jsval_strict_equal(value, search, &eq);
+        jsval_release(value);
+        if(FAILED(hres))
+            return hres;
+        if(eq) {
+            if(r) *r = jsval_number(i);
+            return S_OK;
+        }
+    }
+
+    if(r) *r = jsval_number(-1);
+    return S_OK;
+}
+
 /* ECMA-262 3rd Edition    15.4.4.13 */
 static HRESULT Array_unshift(script_ctx_t *ctx, vdisp_t *vthis, WORD flags, unsigned argc, jsval_t *argv,
         jsval_t *r)
@@ -1044,6 +1100,7 @@ static void Array_on_put(jsdisp_t *dispex, const WCHAR *name)
 
 static const builtin_prop_t Array_props[] = {
     {concatW,                Array_concat,               PROPF_METHOD|1},
+    {indexOfW,               Array_indexOf,              PROPF_ES5|PROPF_METHOD|1},
     {joinW,                  Array_join,                 PROPF_METHOD|1},
     {lengthW,                NULL,0,                     Array_get_length, Array_set_length},
     {popW,                   Array_pop,                  PROPF_METHOD},
diff --git a/dlls/jscript/engine.c b/dlls/jscript/engine.c
index bd14a35..d7a5a46 100644
--- a/dlls/jscript/engine.c
+++ b/dlls/jscript/engine.c
@@ -520,7 +520,7 @@ static HRESULT disp_cmp(IDispatch *disp1, IDispatch *disp2, BOOL *ret)
 }
 
 /* ECMA-262 3rd Edition    11.9.6 */
-static HRESULT jsval_strict_equal(jsval_t lval, jsval_t rval, BOOL *ret)
+HRESULT jsval_strict_equal(jsval_t lval, jsval_t rval, BOOL *ret)
 {
     jsval_type_t type = jsval_type(lval);
 
diff --git a/dlls/jscript/jscript.h b/dlls/jscript/jscript.h
index 119d416..8678619 100644
--- a/dlls/jscript/jscript.h
+++ b/dlls/jscript/jscript.h
@@ -341,6 +341,8 @@ HRESULT to_string(script_ctx_t*,jsval_t,jsstr_t**) DECLSPEC_HIDDEN;
 HRESULT to_flat_string(script_ctx_t*,jsval_t,jsstr_t**,const WCHAR**) DECLSPEC_HIDDEN;
 HRESULT to_object(script_ctx_t*,jsval_t,IDispatch**) DECLSPEC_HIDDEN;
 
+HRESULT jsval_strict_equal(jsval_t,jsval_t,BOOL*) DECLSPEC_HIDDEN;
+
 HRESULT variant_change_type(script_ctx_t*,VARIANT*,VARIANT*,VARTYPE) DECLSPEC_HIDDEN;
 
 HRESULT decode_source(WCHAR*) DECLSPEC_HIDDEN;
diff --git a/dlls/mshtml/tests/documentmode.js b/dlls/mshtml/tests/documentmode.js
index a506a16..b9ac40e 100644
--- a/dlls/mshtml/tests/documentmode.js
+++ b/dlls/mshtml/tests/documentmode.js
@@ -123,6 +123,7 @@ function test_javascript() {
     test_exposed("JSON", g, v >= 8);
     test_exposed("now", Date, true);
     test_exposed("isArray", Array, v >= 9);
+    test_exposed("indexOf", Array.prototype, v >= 9);
 
     next_test();
 }
diff --git a/dlls/mshtml/tests/es5.js b/dlls/mshtml/tests/es5.js
index 29af64e..9f87e99 100644
--- a/dlls/mshtml/tests/es5.js
+++ b/dlls/mshtml/tests/es5.js
@@ -27,6 +27,34 @@ function test_date_now() {
     next_test();
 }
 
+function test_indexOf() {
+    function expect(array, args, exr) {
+        var r = Array.prototype.indexOf.apply(array, args);
+        ok(r == exr, "indexOf returned " + r + " expected " + exr);
+    }
+
+    ok(Array.prototype.indexOf.length == 1, "indexOf.length = " + Array.prototype.indexOf.length);
+
+    expect([1,2,3], [2], 1);
+    expect([1,undefined,3], [undefined], 1);
+    expect([1,undefined,3], [], 1);
+    expect([1,,3], [undefined], -1);
+    expect([1,2,3,4,5,6], [2, 2], -1);
+    expect([1,2,3,4,5,6], [5, -1], -1);
+    expect([1,2,3,4,5,6], [5, -2], 4);
+    expect([1,2,3,4,5,6], [5, -20], 4);
+    expect([1,2,3,4,5,6], [5, 20], -1);
+    expect("abc", ["b"], 1);
+    expect(true, [true], -1);
+    expect({"4": 4, length: 5}, [4], 4);
+    expect({"4": 4, length: 5}, [undefined], -1);
+    expect({"4": 4, length: 3}, [4], -1);
+    expect({"test": true}, [true], -1);
+    expect([1,2,3], [2, 1.9], 1);
+
+    next_test();
+}
+
 function test_isArray() {
     function expect_array(a, exr) {
         var r = Array.isArray(a);
@@ -47,5 +75,6 @@ function test_isArray() {
 
 var tests = [
     test_date_now,
+    test_indexOf,
     test_isArray
 ];




More information about the wine-cvs mailing list