[turbofan] Heap broker for JSCreateLowering::ReduceJSCreateArguments

Bug: v8:7790
Change-Id: I5e12f49038f569187b751cc07a3bfad5eb904949
Reviewed-on: https://chromium-review.googlesource.com/1121460
Commit-Queue: Jaroslav Sevcik <jarin@chromium.org>
Reviewed-by: Georg Neis <neis@chromium.org>
Cr-Commit-Position: refs/heads/master@{#54131}
This commit is contained in:
Jaroslav Sevcik 2018-07-02 12:48:52 +02:00 committed by Commit Bot
parent a383aa33e5
commit 9502913612
4 changed files with 100 additions and 31 deletions

View File

@ -162,14 +162,14 @@ Reduction JSCreateLowering::ReduceJSCreate(Node* node) {
} }
Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) { Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
DisallowHandleDereference disallow_handle_dereference;
DCHECK_EQ(IrOpcode::kJSCreateArguments, node->opcode()); DCHECK_EQ(IrOpcode::kJSCreateArguments, node->opcode());
CreateArgumentsType type = CreateArgumentsTypeOf(node->op()); CreateArgumentsType type = CreateArgumentsTypeOf(node->op());
Node* const frame_state = NodeProperties::GetFrameStateInput(node); Node* const frame_state = NodeProperties::GetFrameStateInput(node);
Node* const outer_state = frame_state->InputAt(kFrameStateOuterStateInput); Node* const outer_state = frame_state->InputAt(kFrameStateOuterStateInput);
Node* const control = graph()->start(); Node* const control = graph()->start();
FrameStateInfo state_info = FrameStateInfoOf(frame_state->op()); FrameStateInfo state_info = FrameStateInfoOf(frame_state->op());
Handle<SharedFunctionInfo> shared = SharedFunctionInfoRef shared(state_info.shared_info().ToHandleChecked());
state_info.shared_info().ToHandleChecked();
// Use the ArgumentsAccessStub for materializing both mapped and unmapped // Use the ArgumentsAccessStub for materializing both mapped and unmapped
// arguments object, but only for non-inlined (i.e. outermost) frames. // arguments object, but only for non-inlined (i.e. outermost) frames.
@ -177,7 +177,7 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
switch (type) { switch (type) {
case CreateArgumentsType::kMappedArguments: { case CreateArgumentsType::kMappedArguments: {
// TODO(mstarzinger): Duplicate parameters are not handled yet. // TODO(mstarzinger): Duplicate parameters are not handled yet.
if (shared->has_duplicate_parameters()) return NoChange(); if (shared.has_duplicate_parameters()) return NoChange();
Node* const callee = NodeProperties::GetValueInput(node, 0); Node* const callee = NodeProperties::GetValueInput(node, 0);
Node* const context = NodeProperties::GetContextInput(node); Node* const context = NodeProperties::GetContextInput(node);
Node* effect = NodeProperties::GetEffectInput(node); Node* effect = NodeProperties::GetEffectInput(node);
@ -185,7 +185,7 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
graph()->NewNode(simplified()->ArgumentsFrame()); graph()->NewNode(simplified()->ArgumentsFrame());
Node* const arguments_length = graph()->NewNode( Node* const arguments_length = graph()->NewNode(
simplified()->ArgumentsLength( simplified()->ArgumentsLength(
shared->internal_formal_parameter_count(), false), shared.internal_formal_parameter_count(), false),
arguments_frame); arguments_frame);
// Allocate the elements backing store. // Allocate the elements backing store.
bool has_aliased_arguments = false; bool has_aliased_arguments = false;
@ -193,11 +193,12 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
effect, control, context, arguments_frame, arguments_length, shared, effect, control, context, arguments_frame, arguments_length, shared,
&has_aliased_arguments); &has_aliased_arguments);
// Load the arguments object map. // Load the arguments object map.
Node* const arguments_map = jsgraph()->HeapConstant( Node* const arguments_map = jsgraph()->Constant(
handle(has_aliased_arguments js_heap_broker(),
? native_context()->fast_aliased_arguments_map() has_aliased_arguments
: native_context()->sloppy_arguments_map(), ? native_context_ref().fast_aliased_arguments_map(
isolate())); js_heap_broker())
: native_context_ref().sloppy_arguments_map(js_heap_broker()));
// Actually allocate and initialize the arguments object. // Actually allocate and initialize the arguments object.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -218,15 +219,16 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
graph()->NewNode(simplified()->ArgumentsFrame()); graph()->NewNode(simplified()->ArgumentsFrame());
Node* const arguments_length = graph()->NewNode( Node* const arguments_length = graph()->NewNode(
simplified()->ArgumentsLength( simplified()->ArgumentsLength(
shared->internal_formal_parameter_count(), false), shared.internal_formal_parameter_count(), false),
arguments_frame); arguments_frame);
// Allocate the elements backing store. // Allocate the elements backing store.
Node* const elements = effect = Node* const elements = effect =
graph()->NewNode(simplified()->NewArgumentsElements(0), graph()->NewNode(simplified()->NewArgumentsElements(0),
arguments_frame, arguments_length, effect); arguments_frame, arguments_length, effect);
// Load the arguments object map. // Load the arguments object map.
Node* const arguments_map = jsgraph()->HeapConstant( Node* const arguments_map = jsgraph()->Constant(
handle(native_context()->strict_arguments_map(), isolate())); js_heap_broker(),
native_context_ref().strict_arguments_map(js_heap_broker()));
// Actually allocate and initialize the arguments object. // Actually allocate and initialize the arguments object.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -246,7 +248,7 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
graph()->NewNode(simplified()->ArgumentsFrame()); graph()->NewNode(simplified()->ArgumentsFrame());
Node* const rest_length = graph()->NewNode( Node* const rest_length = graph()->NewNode(
simplified()->ArgumentsLength( simplified()->ArgumentsLength(
shared->internal_formal_parameter_count(), true), shared.internal_formal_parameter_count(), true),
arguments_frame); arguments_frame);
// Allocate the elements backing store. Since NewArgumentsElements // Allocate the elements backing store. Since NewArgumentsElements
// copies from the end of the arguments adapter frame, this is a suffix // copies from the end of the arguments adapter frame, this is a suffix
@ -255,8 +257,10 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
graph()->NewNode(simplified()->NewArgumentsElements(0), graph()->NewNode(simplified()->NewArgumentsElements(0),
arguments_frame, rest_length, effect); arguments_frame, rest_length, effect);
// Load the JSArray object map. // Load the JSArray object map.
Node* const jsarray_map = jsgraph()->HeapConstant(handle( Node* const jsarray_map = jsgraph()->Constant(
native_context()->js_array_fast_elements_map_index(), isolate())); js_heap_broker(),
native_context_ref().js_array_fast_elements_map_index(
js_heap_broker()));
// Actually allocate and initialize the jsarray. // Actually allocate and initialize the jsarray.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -280,7 +284,7 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
Node* const context = NodeProperties::GetContextInput(node); Node* const context = NodeProperties::GetContextInput(node);
Node* effect = NodeProperties::GetEffectInput(node); Node* effect = NodeProperties::GetEffectInput(node);
// TODO(mstarzinger): Duplicate parameters are not handled yet. // TODO(mstarzinger): Duplicate parameters are not handled yet.
if (shared->has_duplicate_parameters()) return NoChange(); if (shared.has_duplicate_parameters()) return NoChange();
// Choose the correct frame state and frame state info depending on // Choose the correct frame state and frame state info depending on
// whether there conceptually is an arguments adaptor frame in the call // whether there conceptually is an arguments adaptor frame in the call
// chain. // chain.
@ -299,10 +303,12 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
effect, control, args_state, context, shared, &has_aliased_arguments); effect, control, args_state, context, shared, &has_aliased_arguments);
effect = elements->op()->EffectOutputCount() > 0 ? elements : effect; effect = elements->op()->EffectOutputCount() > 0 ? elements : effect;
// Load the arguments object map. // Load the arguments object map.
Node* const arguments_map = jsgraph()->HeapConstant(handle( Node* const arguments_map = jsgraph()->Constant(
has_aliased_arguments ? native_context()->fast_aliased_arguments_map() js_heap_broker(),
: native_context()->sloppy_arguments_map(), has_aliased_arguments
isolate())); ? native_context_ref().fast_aliased_arguments_map(
js_heap_broker())
: native_context_ref().sloppy_arguments_map(js_heap_broker()));
// Actually allocate and initialize the arguments object. // Actually allocate and initialize the arguments object.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -337,8 +343,9 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
Node* const elements = AllocateArguments(effect, control, args_state); Node* const elements = AllocateArguments(effect, control, args_state);
effect = elements->op()->EffectOutputCount() > 0 ? elements : effect; effect = elements->op()->EffectOutputCount() > 0 ? elements : effect;
// Load the arguments object map. // Load the arguments object map.
Node* const arguments_map = jsgraph()->HeapConstant( Node* const arguments_map = jsgraph()->Constant(
handle(native_context()->strict_arguments_map(), isolate())); js_heap_broker(),
native_context_ref().strict_arguments_map(js_heap_broker()));
// Actually allocate and initialize the arguments object. // Actually allocate and initialize the arguments object.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -353,7 +360,7 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
a.FinishAndChange(node); a.FinishAndChange(node);
return Changed(node); return Changed(node);
} else if (type == CreateArgumentsType::kRestParameter) { } else if (type == CreateArgumentsType::kRestParameter) {
int start_index = shared->internal_formal_parameter_count(); int start_index = shared.internal_formal_parameter_count();
// Use inline allocation for all unmapped arguments objects within inlined // Use inline allocation for all unmapped arguments objects within inlined
// (i.e. non-outermost) frames, independent of the object size. // (i.e. non-outermost) frames, independent of the object size.
Node* effect = NodeProperties::GetEffectInput(node); Node* effect = NodeProperties::GetEffectInput(node);
@ -374,8 +381,10 @@ Reduction JSCreateLowering::ReduceJSCreateArguments(Node* node) {
AllocateRestArguments(effect, control, args_state, start_index); AllocateRestArguments(effect, control, args_state, start_index);
effect = elements->op()->EffectOutputCount() > 0 ? elements : effect; effect = elements->op()->EffectOutputCount() > 0 ? elements : effect;
// Load the JSArray object map. // Load the JSArray object map.
Node* const jsarray_map = jsgraph()->HeapConstant(handle( Node* const jsarray_map = jsgraph()->Constant(
native_context()->js_array_fast_elements_map_index(), isolate())); js_heap_broker(),
native_context_ref().js_array_fast_elements_map_index(
js_heap_broker()));
// Actually allocate and initialize the jsarray. // Actually allocate and initialize the jsarray.
AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control); AllocationBuilder a(jsgraph(), js_heap_broker(), effect, control);
Node* properties = jsgraph()->EmptyFixedArrayConstant(); Node* properties = jsgraph()->EmptyFixedArrayConstant();
@ -1502,14 +1511,14 @@ Node* JSCreateLowering::AllocateRestArguments(Node* effect, Node* control,
// given {context}. Serves as backing store for JSCreateArguments nodes. // given {context}. Serves as backing store for JSCreateArguments nodes.
Node* JSCreateLowering::AllocateAliasedArguments( Node* JSCreateLowering::AllocateAliasedArguments(
Node* effect, Node* control, Node* frame_state, Node* context, Node* effect, Node* control, Node* frame_state, Node* context,
Handle<SharedFunctionInfo> shared, bool* has_aliased_arguments) { const SharedFunctionInfoRef& shared, bool* has_aliased_arguments) {
FrameStateInfo state_info = FrameStateInfoOf(frame_state->op()); FrameStateInfo state_info = FrameStateInfoOf(frame_state->op());
int argument_count = state_info.parameter_count() - 1; // Minus receiver. int argument_count = state_info.parameter_count() - 1; // Minus receiver.
if (argument_count == 0) return jsgraph()->EmptyFixedArrayConstant(); if (argument_count == 0) return jsgraph()->EmptyFixedArrayConstant();
// If there is no aliasing, the arguments object elements are not special in // If there is no aliasing, the arguments object elements are not special in
// any way, we can just return an unmapped backing store instead. // any way, we can just return an unmapped backing store instead.
int parameter_count = shared->internal_formal_parameter_count(); int parameter_count = shared.internal_formal_parameter_count();
if (parameter_count == 0) { if (parameter_count == 0) {
return AllocateArguments(effect, control, frame_state); return AllocateArguments(effect, control, frame_state);
} }
@ -1555,11 +1564,11 @@ Node* JSCreateLowering::AllocateAliasedArguments(
// Serves as backing store for JSCreateArguments nodes. // Serves as backing store for JSCreateArguments nodes.
Node* JSCreateLowering::AllocateAliasedArguments( Node* JSCreateLowering::AllocateAliasedArguments(
Node* effect, Node* control, Node* context, Node* arguments_frame, Node* effect, Node* control, Node* context, Node* arguments_frame,
Node* arguments_length, Handle<SharedFunctionInfo> shared, Node* arguments_length, const SharedFunctionInfoRef& shared,
bool* has_aliased_arguments) { bool* has_aliased_arguments) {
// If there is no aliasing, the arguments object elements are not // If there is no aliasing, the arguments object elements are not
// special in any way, we can just return an unmapped backing store. // special in any way, we can just return an unmapped backing store.
int parameter_count = shared->internal_formal_parameter_count(); int parameter_count = shared.internal_formal_parameter_count();
if (parameter_count == 0) { if (parameter_count == 0) {
return graph()->NewNode(simplified()->NewArgumentsElements(0), return graph()->NewNode(simplified()->NewArgumentsElements(0),
arguments_frame, arguments_length, effect); arguments_frame, arguments_length, effect);
@ -1850,6 +1859,10 @@ SimplifiedOperatorBuilder* JSCreateLowering::simplified() const {
return jsgraph()->simplified(); return jsgraph()->simplified();
} }
NativeContextRef JSCreateLowering::native_context_ref() const {
return NativeContextRef(native_context());
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8

View File

@ -80,11 +80,12 @@ class V8_EXPORT_PRIVATE JSCreateLowering final
Node* AllocateRestArguments(Node* effect, Node* control, Node* frame_state, Node* AllocateRestArguments(Node* effect, Node* control, Node* frame_state,
int start_index); int start_index);
Node* AllocateAliasedArguments(Node* effect, Node* control, Node* frame_state, Node* AllocateAliasedArguments(Node* effect, Node* control, Node* frame_state,
Node* context, Handle<SharedFunctionInfo>, Node* context,
const SharedFunctionInfoRef& shared,
bool* has_aliased_arguments); bool* has_aliased_arguments);
Node* AllocateAliasedArguments(Node* effect, Node* control, Node* context, Node* AllocateAliasedArguments(Node* effect, Node* control, Node* context,
Node* arguments_frame, Node* arguments_length, Node* arguments_frame, Node* arguments_length,
Handle<SharedFunctionInfo>, const SharedFunctionInfoRef& shared,
bool* has_aliased_arguments); bool* has_aliased_arguments);
Node* AllocateElements(Node* effect, Node* control, Node* AllocateElements(Node* effect, Node* control,
ElementsKind elements_kind, int capacity, ElementsKind elements_kind, int capacity,
@ -110,6 +111,7 @@ class V8_EXPORT_PRIVATE JSCreateLowering final
JSGraph* jsgraph() const { return jsgraph_; } JSGraph* jsgraph() const { return jsgraph_; }
Isolate* isolate() const; Isolate* isolate() const;
Handle<Context> native_context() const { return native_context_; } Handle<Context> native_context() const { return native_context_; }
NativeContextRef native_context_ref() const;
CommonOperatorBuilder* common() const; CommonOperatorBuilder* common() const;
SimplifiedOperatorBuilder* simplified() const; SimplifiedOperatorBuilder* simplified() const;
CompilationDependencies* dependencies() const { return dependencies_; } CompilationDependencies* dependencies() const { return dependencies_; }

View File

@ -450,6 +450,44 @@ double FixedDoubleArrayRef::get_scalar(int i) const {
return object<FixedDoubleArray>()->get_scalar(i); return object<FixedDoubleArray>()->get_scalar(i);
} }
int SharedFunctionInfoRef::internal_formal_parameter_count() const {
AllowHandleDereference allow_handle_dereference;
return object<SharedFunctionInfo>()->internal_formal_parameter_count();
}
bool SharedFunctionInfoRef::has_duplicate_parameters() const {
AllowHandleDereference allow_handle_dereference;
return object<SharedFunctionInfo>()->has_duplicate_parameters();
}
MapRef NativeContextRef::fast_aliased_arguments_map(
const JSHeapBroker* broker) const {
AllowHandleDereference allow_handle_dereference;
return MapRef(handle(object<Context>()->fast_aliased_arguments_map(),
broker->isolate()));
}
MapRef NativeContextRef::sloppy_arguments_map(
const JSHeapBroker* broker) const {
AllowHandleDereference allow_handle_dereference;
return MapRef(
handle(object<Context>()->sloppy_arguments_map(), broker->isolate()));
}
MapRef NativeContextRef::strict_arguments_map(
const JSHeapBroker* broker) const {
AllowHandleDereference allow_handle_dereference;
return MapRef(
handle(object<Context>()->strict_arguments_map(), broker->isolate()));
}
MapRef NativeContextRef::js_array_fast_elements_map_index(
const JSHeapBroker* broker) const {
AllowHandleDereference allow_handle_dereference;
return MapRef(handle(object<Context>()->js_array_fast_elements_map_index(),
broker->isolate()));
}
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8

View File

@ -69,6 +69,7 @@ class HeapObjectType {
V(Name) \ V(Name) \
V(NativeContext) \ V(NativeContext) \
V(ScriptContextTable) \ V(ScriptContextTable) \
V(SharedFunctionInfo) \
V(Map) V(Map)
#define HEAP_BROKER_KIND_LIST(V) \ #define HEAP_BROKER_KIND_LIST(V) \
@ -194,7 +195,13 @@ class ContextRef : public HeapObjectRef {
class NativeContextRef : public ContextRef { class NativeContextRef : public ContextRef {
public: public:
explicit NativeContextRef(Handle<Object> object); explicit NativeContextRef(Handle<Object> object);
ScriptContextTableRef script_context_table(const JSHeapBroker* broker) const; ScriptContextTableRef script_context_table(const JSHeapBroker* broker) const;
MapRef fast_aliased_arguments_map(const JSHeapBroker* broker) const;
MapRef sloppy_arguments_map(const JSHeapBroker* broker) const;
MapRef strict_arguments_map(const JSHeapBroker* broker) const;
MapRef js_array_fast_elements_map_index(const JSHeapBroker* broker) const;
}; };
class NameRef : public HeapObjectRef { class NameRef : public HeapObjectRef {
@ -282,6 +289,15 @@ class JSArrayRef : public JSObjectRef {
ObjectRef length(const JSHeapBroker* broker) const; ObjectRef length(const JSHeapBroker* broker) const;
}; };
class SharedFunctionInfoRef : public HeapObjectRef {
public:
explicit SharedFunctionInfoRef(Handle<Object> object)
: HeapObjectRef(object) {}
int internal_formal_parameter_count() const;
bool has_duplicate_parameters() const;
};
} // namespace compiler } // namespace compiler
} // namespace internal } // namespace internal
} // namespace v8 } // namespace v8