Skip to content

Test262 #5: Object.create(proto, properties) doesn't iterate built-in property bags (~128 tests) #104

@nickna

Description

@nickna

Motivation

Surfaced during the #69 Object folder rollout (commit 9d16edc). When Object.create's second argument (the property-descriptors map) is a built-in object like Math, Error.prototype, or a function instance, our impl fails to iterate its own enumerable properties.

Per ECMA-262 §20.1.2.2.1 (ObjectDefineProperties):

  1. Let keys be ? props.[OwnPropertyKeys].
  2. For each element nextKey of keys, do
    a. Let propDesc be ? props.[GetOwnProperty].
    b. If propDesc is not undefined and propDesc.[[Enumerable]] is true, then
    i. Let descObj be ? Get(props, nextKey).
    ii. Let desc be ? ToPropertyDescriptor(descObj).

The [[OwnPropertyKeys]] invocation must work uniformly on any object — including built-in singletons.

Sample failing test

test/built-ins/Object/create/15.2.3.5-4-10.js:

Object.defineProperty(Math, "prop", {
  get: function() {
    result = (this === Math);
    return {};
  },
  enumerable: true,
  configurable: true
});

var newObj = Object.create({}, Math);

assert(result, 'result !== true');
assert(newObj.hasOwnProperty("prop"));

The test attaches an enumerable accessor prop to Math, then passes Math as the property-descriptor map. ECMA says iterate Math's own enumerable property keys (just "prop" here, since the standard Math.PI etc. are non-enumerable), invoke the getter, treat the returned object as a descriptor, and define newObj.prop.

Impact

API Bucket Count
Object.create RuntimeError 128

Most are variants of the above pattern: Object.create({}, X) where X is one of Math, Error("msg"), function(){}, String(...), Number(...), Boolean(...), etc.

Suggested approach

  1. Audit Object.create (and the shared ObjectDefineProperties shim that backs it) — the iteration step must call [[OwnPropertyKeys]] on the properties argument regardless of its concrete .NET type.
  2. Verify each built-in singleton type (SharpTSMath, SharpTSError, SharpTSNumber, SharpTSBoolean, etc.) implements OwnPropertyKeys() returning the correct enumerable keys (including any properties dynamically attached via defineProperty).
  3. Cross-check: for...in over Math after defineProperty(Math, "prop", {enumerable: true, ...}) should yield "prop". If that's broken, this fix is upstream of Object.create and lands a multiplier benefit.

Acceptance

  • The 128 Object.create RuntimeError tests flip out of RuntimeError.
  • Object.keys(Math) after a defineProperty with enumerable: true returns the new key.
  • No regressions in Object/keys, Object/getOwnPropertyNames, for-in baselines.

Related

Part of #69. Likely shares root cause with parts of #103 (PropertyKey handling).

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions