Open Bug 1606421 Opened 4 years ago Updated 2 years ago

Function object should have own "arguments" accessor, and Function#arguemnts should unconditionally throw

Categories

(Core :: JavaScript Engine, defect, P3)

71 Branch
defect

Tracking

()

People

(Reporter: 1753733633, Unassigned)

References

Details

User Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.14; rv:71.0) Gecko/20100101 Firefox/71.0

Steps to reproduce:

var a = function(){}
a.hasOwnProperty('arguments')

Actual results:

a.hasOwnProperty('arguments') === false

Expected results:

in chrome, safir, ie
a.hasOwnProperty('arguments') === true

non-strict function objects' arguments property isn't spec-ed, so the behavior is implementation dependent,
so, the result above itself doesn't violates the spec.
however, to implement the common extension (allowing non_strict_function.arguments access),
the only way would be adding own property (see the comment about proposal at the end of this comment)

the details are the following.

What the spec says about function object's arguments property is only that,
it shouldn't have arguments property when it's strict-mode.

https://tc39.es/ecma262/#sec-forbidden-extensions

16.2 Forbidden Extensions

An implementation must not extend this specification in the following ways:

  • ECMAScript function objects defined using syntactic constructors in strict
    mode code must not be created with own properties named "caller" or
    "arguments". Such own properties also must not be created for function
    objects defined using an ArrowFunction , MethodDefinition ,
    GeneratorDeclaration , GeneratorExpression , AsyncGeneratorDeclaration ,
    AsyncGeneratorExpression , ClassDeclaration , ClassExpression ,
    AsyncFunctionDeclaration , AsyncFunctionExpression , or AsyncArrowFunction
    regardless of whether the definition is contained in strict mode code.
    Built-in functions, strict functions created using the Function
    constructor, generator functions created using the Generator constructor,
    async functions created using the AsyncFunction constructor, and functions
    created using the bind method also must not be created with such own
    properties.

then, the spec defines arguments property of Function.prototype, that unconditionally throws.

https://tc39.es/ecma262/#sec-createintrinsics

8.2.2 CreateIntrinsics ( realmRec )

The abstract operation CreateIntrinsics with argument realmRec performs the
following steps:

...
4. Perform
AddRestrictedFunctionProperties(intrinsics.[[%Function.prototype%]],
realmRec).

https://tc39.es/ecma262/#sec-addrestrictedfunctionproperties

9.2.4 AddRestrictedFunctionProperties ( F, realm )

...

  1. Assert: realm.[[Intrinsics]].[[%ThrowTypeError%]] exists and has been
    initialized.
  2. Let thrower be realm.[[Intrinsics]].[[%ThrowTypeError%]].
  3. Perform ! DefinePropertyOrThrow(F, "caller", PropertyDescriptor { [[Get]]:
    thrower, [[Set]]: thrower, [[Enumerable]]: false, [[Configurable]]: true
    }).
  4. Return ! DefinePropertyOrThrow(F, "arguments", PropertyDescriptor {
    [[Get]]: thrower, [[Set]]: thrower, [[Enumerable]]: false,
    [[Configurable]]: true }).

https://tc39.es/ecma262/#table-7

Table 8: Well-Known Intrinsic Objects

%ThrowTypeError%
A function object that unconditionally throws a new instance of %TypeError%

then, what SpiderMonkey implements is slightly different than the spec.
For non-strict function objects, the getter returns arguments object, instead of just throwing.

so, the following code behaves differently, and SpiderMonkey's behavior doesn't follow the spec,
given the thrower conditionally throws, and it doesn't for this case.

(function f() {  return Object.getOwnPropertyDescriptor(Function.prototype, "arguments").get.call(f); })(1, 2, 3)

this behavior is implemented in bug 969478,
and it seems to be that the spec is changed to above after that.

also, there's proposal to modify Function#arguments not to throw unconditionally.

https://github.com/claudepache/es-legacy-function-reflection

I think that is something similar to SpiderMonkey's behavior.

Status: UNCONFIRMED → NEW
Component: Untriaged → JavaScript Engine
Ever confirmed: true
Product: Firefox → Core
See Also: → 969478
Summary: hasOwnProperty('arguments') → Function object should have own "arguments" accessor, and Function#arguemnts should unconditionally throw

also, bug 1527810 is related that it's about caller accessor's behavior

See Also: → 1527810
Priority: -- → P3

Working as intended per Bug 1615704. In particular, the, arguments accessor is inherited from Function.prototype.

Severity: normal → S3
You need to log in before you can comment on or make changes to this bug.