Ignore:
Timestamp:
Aug 27, 2020, 5:27:19 PM (5 years ago)
Author:
Alexey Shvayka
Message:

proto in object literal should perform SetPrototypeOf directly
https://bugs.webkit.org/show_bug.cgi?id=215769

Reviewed by Ross Kirsling.

JSTests:

  • microbenchmarks/object-literal-underscore-proto-setter.js: Added.
  • stress/syntax-checker-duplicate-underscore-proto.js:

Rewrite the test to ensure each eval() call throws a SyntaxError.

Source/JavaScriptCore:

To fix proto usage in object literals if Object.prototype.proto is overridden
or removed, this patch sets the Prototype directly, aligning JSC with V8 and
SpiderMonkey. We are safe to skip method table lookups and cycle checks, as the
spec [1] calls SetPrototypeOf on newly created (unreferenced) ordinary objects.

This change removes PropertyNode::PutType because its only purpose was to accomodate
proto in object literals. Since emitPutConstantProperty() handles static public
class fields, which don't need super binding, PropertyNode::isUnderscoreProtoSetter()
is extended to reject class properties.

This patch speeds up creating object literals with proto by 25%.

[1]: https://tc39.es/ecma262/#sec-__proto__-property-names-in-object-initializers (step 7.a)

  • bytecompiler/BytecodeGenerator.cpp:

(JSC::BytecodeGenerator::emitDirectPutById):
(JSC::BytecodeGenerator::emitDirectSetPrototypeOf):

  1. Remove unused dst parameter to align with other put methods.
  2. Remove divot* parameters as it's cumbersome to pass them through, and globalFuncSetPrototypeDirect() never throws anyway.
  • bytecompiler/BytecodeGenerator.h:
  • bytecompiler/NodesCodegen.cpp:

(JSC::PropertyListNode::emitPutConstantProperty):
(JSC::BytecodeIntrinsicNode::emit_intrinsic_putByIdDirect):
(JSC::BytecodeIntrinsicNode::emit_intrinsic_putByIdDirectPrivate):
(JSC::ClassExprNode::emitBytecode):

  • parser/ASTBuilder.h:

(JSC::ASTBuilder::createGetterOrSetterProperty):
(JSC::ASTBuilder::createProperty):
(JSC::ASTBuilder::isUnderscoreProtoSetter const):

  • parser/NodeConstructors.h:

(JSC::PropertyNode::PropertyNode):

  • parser/Nodes.h:
  • parser/Parser.cpp:

(JSC::Parser<LexerType>::parseClass):
(JSC::Parser<LexerType>::parseProperty):

  • parser/SyntaxChecker.h:

(JSC::SyntaxChecker::createProperty):

  • runtime/JSGlobalObjectFunctions.cpp:

(JSC::globalFuncSetPrototypeDirect):

  1. Ignore a prototype value of incorrect type as per spec [1], which is unobservable for call sites in ClassExprNode::emitBytecode().
  2. Assert that JSObject::setPrototypeDirect() doesn't throw.

LayoutTests:

  • js/script-tests/object-literal-direct-put.js:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/ChangeLog

    r266257 r266264  
     12020-08-27  Alexey Shvayka  <[email protected]>
     2
     3        __proto__ in object literal should perform [[SetPrototypeOf]] directly
     4        https://bugs.webkit.org/show_bug.cgi?id=215769
     5
     6        Reviewed by Ross Kirsling.
     7
     8        To fix __proto__ usage in object literals if Object.prototype.__proto__ is overridden
     9        or removed, this patch sets the [[Prototype]] directly, aligning JSC with V8 and
     10        SpiderMonkey. We are safe to skip method table lookups and cycle checks, as the
     11        spec [1] calls [[SetPrototypeOf]] on newly created (unreferenced) ordinary objects.
     12
     13        This change removes PropertyNode::PutType because its only purpose was to accomodate
     14        __proto__ in object literals. Since emitPutConstantProperty() handles static public
     15        class fields, which don't need `super` binding, PropertyNode::isUnderscoreProtoSetter()
     16        is extended to reject class properties.
     17
     18        This patch speeds up creating object literals with __proto__ by 25%.
     19
     20        [1]: https://tc39.es/ecma262/#sec-__proto__-property-names-in-object-initializers (step 7.a)
     21
     22        * bytecompiler/BytecodeGenerator.cpp:
     23        (JSC::BytecodeGenerator::emitDirectPutById):
     24        (JSC::BytecodeGenerator::emitDirectSetPrototypeOf):
     25        1. Remove unused `dst` parameter to align with other `put` methods.
     26        2. Remove `divot*` parameters as it's cumbersome to pass them through,
     27           and globalFuncSetPrototypeDirect() never throws anyway.
     28
     29        * bytecompiler/BytecodeGenerator.h:
     30        * bytecompiler/NodesCodegen.cpp:
     31        (JSC::PropertyListNode::emitPutConstantProperty):
     32        (JSC::BytecodeIntrinsicNode::emit_intrinsic_putByIdDirect):
     33        (JSC::BytecodeIntrinsicNode::emit_intrinsic_putByIdDirectPrivate):
     34        (JSC::ClassExprNode::emitBytecode):
     35        * parser/ASTBuilder.h:
     36        (JSC::ASTBuilder::createGetterOrSetterProperty):
     37        (JSC::ASTBuilder::createProperty):
     38        (JSC::ASTBuilder::isUnderscoreProtoSetter const):
     39        * parser/NodeConstructors.h:
     40        (JSC::PropertyNode::PropertyNode):
     41        * parser/Nodes.h:
     42        * parser/Parser.cpp:
     43        (JSC::Parser<LexerType>::parseClass):
     44        (JSC::Parser<LexerType>::parseProperty):
     45        * parser/SyntaxChecker.h:
     46        (JSC::SyntaxChecker::createProperty):
     47        * runtime/JSGlobalObjectFunctions.cpp:
     48        (JSC::globalFuncSetPrototypeDirect):
     49        1. Ignore a prototype value of incorrect type as per spec [1],
     50           which is unobservable for call sites in ClassExprNode::emitBytecode().
     51        2. Assert that JSObject::setPrototypeDirect() doesn't throw.
     52
    1532020-08-27  Yusuke Suzuki  <[email protected]>
    254
Note: See TracChangeset for help on using the changeset viewer.