jscript: Add Object.getOwnPropertyNames implementation.

Signed-off-by: Jacek Caban <jacek@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Jacek Caban 2021-04-20 19:12:07 +02:00 committed by Alexandre Julliard
parent c4948c428a
commit 9885de45af
4 changed files with 59 additions and 9 deletions

View file

@ -2385,7 +2385,7 @@ HRESULT jsdisp_next_prop(jsdisp_t *obj, DISPID id, enum jsdisp_enum_type enum_ty
continue;
if(enum_type != JSDISP_ENUM_ALL && iter->type == PROP_PROTREF)
continue;
if(!(get_flags(obj, iter) & PROPF_ENUMERABLE))
if(enum_type != JSDISP_ENUM_OWN && !(get_flags(obj, iter) & PROPF_ENUMERABLE))
continue;
*ret = prop_to_id(obj, iter);
return S_OK;

View file

@ -292,6 +292,7 @@ void jsdisp_release(jsdisp_t*) DECLSPEC_HIDDEN;
enum jsdisp_enum_type {
JSDISP_ENUM_ALL,
JSDISP_ENUM_OWN,
JSDISP_ENUM_OWN_ENUMERABLE
};

View file

@ -625,8 +625,7 @@ static HRESULT Object_getPrototypeOf(script_ctx_t *ctx, vdisp_t *jsthis, WORD fl
return S_OK;
}
static HRESULT Object_keys(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
unsigned argc, jsval_t *argv, jsval_t *r)
static HRESULT object_keys(script_ctx_t *ctx, jsval_t arg, enum jsdisp_enum_type enum_type, jsval_t *r)
{
DISPID id = DISPID_STARTENUM;
jsdisp_t *obj, *array;
@ -634,14 +633,12 @@ static HRESULT Object_keys(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
jsstr_t *key;
HRESULT hres;
if(!argc || !is_object_instance(argv[0])) {
FIXME("invalid arguments %s\n", debugstr_jsval(argv[0]));
if(!is_object_instance(arg) || !get_object(arg)) {
FIXME("invalid arguments %s\n", debugstr_jsval(arg));
return E_NOTIMPL;
}
TRACE("(%s)\n", debugstr_jsval(argv[0]));
obj = to_jsdisp(get_object(argv[0]));
obj = to_jsdisp(get_object(arg));
if(!obj) {
FIXME("Non-JS object\n");
return E_NOTIMPL;
@ -652,7 +649,7 @@ static HRESULT Object_keys(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
return hres;
do {
hres = jsdisp_next_prop(obj, id, JSDISP_ENUM_OWN_ENUMERABLE, &id);
hres = jsdisp_next_prop(obj, id, enum_type, &id);
if(hres != S_OK)
break;
@ -671,6 +668,26 @@ static HRESULT Object_keys(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
return hres;
}
static HRESULT Object_keys(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
unsigned argc, jsval_t *argv, jsval_t *r)
{
jsval_t arg = argc ? argv[0] : jsval_undefined();
TRACE("(%s)\n", debugstr_jsval(arg));
return object_keys(ctx, arg, JSDISP_ENUM_OWN_ENUMERABLE, r);
}
static HRESULT Object_getOwnPropertyNames(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags,
unsigned argc, jsval_t *argv, jsval_t *r)
{
jsval_t arg = argc ? argv[0] : jsval_undefined();
TRACE("(%s)\n", debugstr_jsval(arg));
return object_keys(ctx, arg, JSDISP_ENUM_OWN, r);
}
static HRESULT Object_preventExtensions(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags, unsigned argc, jsval_t *argv, jsval_t *r)
{
jsdisp_t *obj;
@ -810,6 +827,7 @@ static const builtin_prop_t ObjectConstr_props[] = {
{L"defineProperty", Object_defineProperty, PROPF_ES5|PROPF_METHOD|2},
{L"freeze", Object_freeze, PROPF_ES5|PROPF_METHOD|1},
{L"getOwnPropertyDescriptor", Object_getOwnPropertyDescriptor, PROPF_ES5|PROPF_METHOD|2},
{L"getOwnPropertyNames", Object_getOwnPropertyNames, PROPF_ES5|PROPF_METHOD|1},
{L"getPrototypeOf", Object_getPrototypeOf, PROPF_ES5|PROPF_METHOD|1},
{L"isExtensible", Object_isExtensible, PROPF_ES5|PROPF_METHOD|1},
{L"isFrozen", Object_isFrozen, PROPF_ES5|PROPF_METHOD|1},

View file

@ -892,9 +892,40 @@ sync_test("keys", function() {
keys = Object.keys(o).sort().join();
ok(keys === "test", "keys = " + keys);
Object.defineProperty(o, "defined", { value: 3, enumerable: false });
keys = Object.keys(o).sort().join();
ok(keys === "test", "keys = " + keys);
keys = Object.keys([]).sort().join();
ok(keys === "", "keys([]) = " + keys);
ok(Object.keys.length === 1, "Object.keys.length = " + Object.keys.length);
});
sync_test("getOwnPropertyNames", function() {
var o = { a: 1, b: 2, c: 3 };
var names = Object.getOwnPropertyNames(o).sort().join();
ok(names === "a,b,c", "names = " + names);
o = Object.create(o);
names = Object.getOwnPropertyNames(o).sort().join();
ok(names === "", "names = " + names);
o.test = 1;
names = Object.getOwnPropertyNames(o).sort().join();
ok(names === "test", "names = " + names);
Object.defineProperty(o, "defined", { value: 3, enumerable: false });
names = Object.getOwnPropertyNames(o).sort().join();
ok(names === "defined,test", "names = " + names);
names = Object.getOwnPropertyNames([]).sort().join();
todo_wine.
ok(names === "length", "names = " + names);
ok(Object.getOwnPropertyNames.length === 1, "Object.getOwnPropertyNames.length = " + Object.getOwnPropertyNames.length);
});
sync_test("reduce", function() {
var r, array;