Ignore:
Timestamp:
Jan 2, 2021, 12:46:24 PM (4 years ago)
Author:
[email protected]
Message:

[JSC] Remove unnecessary mov bytecodes when performing simple object pattern destructuring to variables
https://bugs.webkit.org/show_bug.cgi?id=220219

Reviewed by Alexey Shvayka.

JSTests:

  • stress/object-pattern-simple-fast-path.js: Added.

(shouldBe):
(shouldThrow):
(test1):

Source/JavaScriptCore:

Currently, we are first puts object pattern's expression into temporary variable, and then, we store it into local variable register.

The following code

({ data } = object);

emits this kind of bytecode.

get_by_id dst:loc10, base:loc9, property:0
mov dst:loc6, src:loc10

However, this should be

get_by_id dst:loc6, base:loc9, property:0

We are emitting many unnecessary movs since this destructuring pattern is common. Increasing amount of mov (1) discourages inlining unnecessarily and (2) simply makes
bytecode memory large. Since this is very common pattern, we should carefully optimize it to remove such unnecessary movs.

This patch looks into pattern when performing object pattern destructuring. And avoid emitting mov when it is possible. There are some cases we cannot remove movs, so
this patch's writableDirectBindingIfPossible looks into whether this is possible (& profitable).

  • bytecompiler/NodesCodegen.cpp:

(JSC::ObjectPatternNode::bindValue const):
(JSC::BindingNode::writableDirectBindingIfPossible const):
(JSC::BindingNode::finishDirectBindingAssignment const):
(JSC::AssignmentElementNode::writableDirectBindingIfPossible const):
(JSC::AssignmentElementNode::finishDirectBindingAssignment const):

  • parser/Nodes.h:

(JSC::DestructuringPatternNode::writableDirectBindingIfPossible const):
(JSC::DestructuringPatternNode::finishDirectBindingAssignment const):

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/parser/Nodes.h

    r269922 r271121  
    23752375        virtual bool isRestParameter() const { return false; }
    23762376        virtual RegisterID* emitDirectBinding(BytecodeGenerator&, RegisterID*, ExpressionNode*) { return nullptr; }
     2377
     2378        virtual RegisterID* writableDirectBindingIfPossible(BytecodeGenerator&) const { return nullptr; }
     2379        virtual void finishDirectBindingAssignment(BytecodeGenerator&) const { }
    23772380       
    23782381    protected:
     
    24612464        const JSTextPosition& divotStart() const { return m_divotStart; }
    24622465        const JSTextPosition& divotEnd() const { return m_divotEnd; }
     2466
     2467        RegisterID* writableDirectBindingIfPossible(BytecodeGenerator&) const final;
     2468        void finishDirectBindingAssignment(BytecodeGenerator&) const;
    24632469       
    24642470    private:
     
    24992505        const JSTextPosition& divotStart() const { return m_divotStart; }
    25002506        const JSTextPosition& divotEnd() const { return m_divotEnd; }
     2507
     2508        RegisterID* writableDirectBindingIfPossible(BytecodeGenerator&) const final;
     2509        void finishDirectBindingAssignment(BytecodeGenerator&) const;
    25012510
    25022511    private:
Note: See TracChangeset for help on using the changeset viewer.