1014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Copyright 2015 the V8 project authors. All rights reserved. 2014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Use of this source code is governed by a BSD-style license that can be 3014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// found in the LICENSE file. 4014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 5014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#ifndef V8_COMPILER_JS_NATIVE_CONTEXT_SPECIALIZATION_H_ 6014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#define V8_COMPILER_JS_NATIVE_CONTEXT_SPECIALIZATION_H_ 7014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 8014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/base/flags.h" 9014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#include "src/compiler/graph-reducer.h" 10014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 11014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace v8 { 12014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace internal { 13014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 14014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Forward declarations. 15014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass CompilationDependencies; 16014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass Factory; 17014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass FeedbackNexus; 18014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass TypeCache; 19014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 20014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 21014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochnamespace compiler { 22014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 23014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Forward declarations. 24014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochenum class AccessMode; 25014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass CommonOperatorBuilder; 26014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass JSGraph; 27014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass JSOperatorBuilder; 28014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass MachineOperatorBuilder; 29014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass SimplifiedOperatorBuilder; 30014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 31014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 32014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// Specializes a given JSGraph to a given native context, potentially constant 33014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// folding some {LoadGlobal} nodes or strength reducing some {StoreGlobal} 34014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// nodes. And also specializes {LoadNamed} and {StoreNamed} nodes according 35014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch// to type feedback (if available). 36014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdochclass JSNativeContextSpecialization final : public AdvancedReducer { 37014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch public: 38014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch // Flags that control the mode of operation. 39014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch enum Flag { 40014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch kNoFlags = 0u, 41342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch kBailoutOnUninitialized = 1u << 0, 42342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch kDeoptimizationEnabled = 1u << 1, 43014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch }; 44014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch typedef base::Flags<Flag> Flags; 45014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 46014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch JSNativeContextSpecialization(Editor* editor, JSGraph* jsgraph, Flags flags, 47014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MaybeHandle<Context> native_context, 48014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch CompilationDependencies* dependencies, 49014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Zone* zone); 50014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 51014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction Reduce(Node* node) final; 52014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 53014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch private: 54342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch Reduction ReduceJSLoadContext(Node* node); 55014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceJSLoadNamed(Node* node); 56014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceJSStoreNamed(Node* node); 57014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceJSLoadProperty(Node* node); 58014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceJSStoreProperty(Node* node); 59014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 60014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceElementAccess(Node* node, Node* index, Node* value, 61014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MapHandleList const& receiver_maps, 62014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch AccessMode access_mode, 63014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch LanguageMode language_mode, 64014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch KeyedAccessStoreMode store_mode); 65014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceKeyedAccess(Node* node, Node* index, Node* value, 66014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch FeedbackNexus const& nexus, 67014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch AccessMode access_mode, 68014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch LanguageMode language_mode, 69014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch KeyedAccessStoreMode store_mode); 70014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Reduction ReduceNamedAccess(Node* node, Node* value, 71342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch FeedbackNexus const& nexus, Handle<Name> name, 72342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch AccessMode access_mode, 73342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch LanguageMode language_mode); 74342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch Reduction ReduceNamedAccess(Node* node, Node* value, 75014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MapHandleList const& receiver_maps, 76014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Handle<Name> name, AccessMode access_mode, 77014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch LanguageMode language_mode, 78014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Node* index = nullptr); 79014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 80342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch Reduction ReduceSoftDeoptimize(Node* node); 81342c50ce1624b485728b9a4fc41d8bbf37eb46cfBen Murdoch 82014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch // Adds stability dependencies on all prototypes of every class in 83014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch // {receiver_type} up to (and including) the {holder}. 84014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch void AssumePrototypesStable(Type* receiver_type, 85014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Handle<Context> native_context, 86014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Handle<JSObject> holder); 87014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 88537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // Extract receiver maps from {nexus} and filter based on {receiver} if 89537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // possible. 90537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch bool ExtractReceiverMaps(Node* receiver, Node* effect, 91537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch FeedbackNexus const& nexus, 92537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch MapHandleList* receiver_maps); 93537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch 94537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // Try to infer a map for the given {receiver} at the current {effect}. 95537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // If a map is returned then you can be sure that the {receiver} definitely 96537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // has the returned map at this point in the program (identified by {effect}). 97537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch MaybeHandle<Map> InferReceiverMap(Node* receiver, Node* effect); 98537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // Try to infer a root map for the {receiver} independent of the current 99537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch // program location. 100537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch MaybeHandle<Map> InferReceiverRootMap(Node* receiver); 101537ba893e2530051ec7f296e769fdd37bb4ae4a0Ben Murdoch 102014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch // Retrieve the native context from the given {node} if known. 103014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MaybeHandle<Context> GetNativeContext(Node* node); 104014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 105014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Graph* graph() const; 106014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch JSGraph* jsgraph() const { return jsgraph_; } 107014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Isolate* isolate() const; 108014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Factory* factory() const; 109014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch CommonOperatorBuilder* common() const; 110014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch JSOperatorBuilder* javascript() const; 111014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch SimplifiedOperatorBuilder* simplified() const; 112014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MachineOperatorBuilder* machine() const; 113014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Flags flags() const { return flags_; } 114014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MaybeHandle<Context> native_context() const { return native_context_; } 115014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch CompilationDependencies* dependencies() const { return dependencies_; } 116014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Zone* zone() const { return zone_; } 117014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 118014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch JSGraph* const jsgraph_; 119014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Flags const flags_; 120014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch MaybeHandle<Context> native_context_; 121014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch CompilationDependencies* const dependencies_; 122014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch Zone* const zone_; 123014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch TypeCache const& type_cache_; 124014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 125014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch DISALLOW_COPY_AND_ASSIGN(JSNativeContextSpecialization); 126014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch}; 127014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 128014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben MurdochDEFINE_OPERATORS_FOR_FLAGS(JSNativeContextSpecialization::Flags) 129014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 130014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch} // namespace compiler 131014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch} // namespace internal 132014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch} // namespace v8 133014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch 134014dc512cdd3e367bee49a713fdc5ed92584a3e5Ben Murdoch#endif // V8_COMPILER_JS_NATIVE_CONTEXT_SPECIALIZATION_H_ 135