Commit 58ad0bbe authored by jgruber's avatar jgruber Committed by Commit Bot

[regexp] Inline regexp literal allocation

This inlines the allocation of regexp literals when a boilerplate exists.

Bug: v8:6605,v8:6556
Change-Id: If0f1b9dedf8a7de1ec51c394fe39cf21d2413ac5
Reviewed-on: https://chromium-review.googlesource.com/575240
Commit-Queue: Jakob Gruber <jgruber@chromium.org>
Reviewed-by: 's avatarBenedikt Meurer <bmeurer@chromium.org>
Reviewed-by: 's avatarJaroslav Sevcik <jarin@chromium.org>
Cr-Commit-Position: refs/heads/master@{#46780}
parent 2bce4880
......@@ -427,6 +427,14 @@ FieldAccess AccessBuilder::ForJSIteratorResultValue() {
return access;
}
// static
FieldAccess AccessBuilder::ForJSRegExpData() {
FieldAccess access = {kTaggedBase, JSRegExp::kDataOffset,
MaybeHandle<Name>(), MaybeHandle<Map>(),
Type::NonInternal(), MachineType::AnyTagged(),
kFullWriteBarrier};
return access;
}
// static
FieldAccess AccessBuilder::ForJSRegExpFlags() {
......@@ -437,6 +445,14 @@ FieldAccess AccessBuilder::ForJSRegExpFlags() {
return access;
}
// static
FieldAccess AccessBuilder::ForJSRegExpLastIndex() {
FieldAccess access = {kTaggedBase, JSRegExp::kLastIndexOffset,
MaybeHandle<Name>(), MaybeHandle<Map>(),
Type::NonInternal(), MachineType::AnyTagged(),
kFullWriteBarrier};
return access;
}
// static
FieldAccess AccessBuilder::ForJSRegExpSource() {
......
......@@ -145,9 +145,15 @@ class V8_EXPORT_PRIVATE AccessBuilder final
// Provides access to JSIteratorResult::value() field.
static FieldAccess ForJSIteratorResultValue();
// Provides access to JSRegExp::data() field.
static FieldAccess ForJSRegExpData();
// Provides access to JSRegExp::flags() field.
static FieldAccess ForJSRegExpFlags();
// Provides access to JSRegExp::last_index() field.
static FieldAccess ForJSRegExpLastIndex();
// Provides access to JSRegExp::source() field.
static FieldAccess ForJSRegExpSource();
......
......@@ -220,7 +220,9 @@ Reduction JSCreateLowering::Reduce(Node* node) {
return ReduceJSCreateKeyValueArray(node);
case IrOpcode::kJSCreateLiteralArray:
case IrOpcode::kJSCreateLiteralObject:
return ReduceJSCreateLiteral(node);
return ReduceJSCreateLiteralArrayOrObject(node);
case IrOpcode::kJSCreateLiteralRegExp:
return ReduceJSCreateLiteralRegExp(node);
case IrOpcode::kJSCreateEmptyLiteralArray:
return ReduceJSCreateEmptyLiteralArray(node);
case IrOpcode::kJSCreateFunctionContext:
......@@ -892,7 +894,7 @@ Reduction JSCreateLowering::ReduceJSCreateKeyValueArray(Node* node) {
return Changed(node);
}
Reduction JSCreateLowering::ReduceJSCreateLiteral(Node* node) {
Reduction JSCreateLowering::ReduceJSCreateLiteralArrayOrObject(Node* node) {
DCHECK(node->opcode() == IrOpcode::kJSCreateLiteralArray ||
node->opcode() == IrOpcode::kJSCreateLiteralObject);
CreateLiteralParameters const& p = CreateLiteralParametersOf(node->op());
......@@ -921,6 +923,26 @@ Reduction JSCreateLowering::ReduceJSCreateLiteral(Node* node) {
return NoChange();
}
Reduction JSCreateLowering::ReduceJSCreateLiteralRegExp(Node* node) {
DCHECK(node->opcode() == IrOpcode::kJSCreateLiteralRegExp);
CreateLiteralParameters const& p = CreateLiteralParametersOf(node->op());
Node* effect = NodeProperties::GetEffectInput(node);
Node* control = NodeProperties::GetControlInput(node);
Handle<FeedbackVector> feedback_vector;
if (GetSpecializationFeedbackVector(node).ToHandle(&feedback_vector)) {
FeedbackSlot slot(FeedbackVector::ToSlot(p.index()));
Handle<Object> maybe_boilerplate(feedback_vector->Get(slot), isolate());
if (maybe_boilerplate->IsJSRegExp()) {
Node* value = effect = AllocateLiteralRegExp(
effect, control, Handle<JSRegExp>::cast(maybe_boilerplate));
ReplaceWithValue(node, value, effect, control);
return Replace(value);
}
}
return NoChange();
}
Reduction JSCreateLowering::ReduceJSCreateEmptyLiteralArray(Node* node) {
DCHECK_EQ(node->opcode(), IrOpcode::kJSCreateEmptyLiteralArray);
int literal_index = OpParameter<int>(node);
......@@ -1414,6 +1436,44 @@ Node* JSCreateLowering::AllocateFastLiteralElements(
return builder.Finish();
}
Node* JSCreateLowering::AllocateLiteralRegExp(Node* effect, Node* control,
Handle<JSRegExp> boilerplate) {
Handle<Map> boilerplate_map(boilerplate->map(), isolate());
// Sanity check that JSRegExp object layout hasn't changed.
STATIC_ASSERT(JSRegExp::kDataOffset == JSObject::kHeaderSize);
STATIC_ASSERT(JSRegExp::kSourceOffset ==
JSRegExp::kDataOffset + kPointerSize);
STATIC_ASSERT(JSRegExp::kFlagsOffset ==
JSRegExp::kSourceOffset + kPointerSize);
STATIC_ASSERT(JSRegExp::kSize == JSRegExp::kFlagsOffset + kPointerSize);
STATIC_ASSERT(JSRegExp::kLastIndexOffset == JSRegExp::kSize);
STATIC_ASSERT(JSRegExp::kInObjectFieldCount == 1); // LastIndex.
const PretenureFlag pretenure = NOT_TENURED;
const int size =
JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize;
AllocationBuilder builder(jsgraph(), effect, control);
builder.Allocate(size, pretenure, Type::For(boilerplate_map));
builder.Store(AccessBuilder::ForMap(), boilerplate_map);
builder.Store(AccessBuilder::ForJSObjectProperties(),
handle(boilerplate->raw_properties_or_hash(), isolate()));
builder.Store(AccessBuilder::ForJSObjectElements(),
handle(boilerplate->elements(), isolate()));
builder.Store(AccessBuilder::ForJSRegExpData(),
handle(boilerplate->data(), isolate()));
builder.Store(AccessBuilder::ForJSRegExpSource(),
handle(boilerplate->source(), isolate()));
builder.Store(AccessBuilder::ForJSRegExpFlags(),
handle(boilerplate->flags(), isolate()));
builder.Store(AccessBuilder::ForJSRegExpLastIndex(),
handle(boilerplate->last_index(), isolate()));
return builder.Finish();
}
MaybeHandle<FeedbackVector> JSCreateLowering::GetSpecializationFeedbackVector(
Node* node) {
Node* const closure = NodeProperties::GetValueInput(node, 0);
......
......@@ -55,7 +55,8 @@ class V8_EXPORT_PRIVATE JSCreateLowering final
Reduction ReduceJSCreateIterResultObject(Node* node);
Reduction ReduceJSCreateKeyValueArray(Node* node);
Reduction ReduceJSCreateEmptyLiteralArray(Node* node);
Reduction ReduceJSCreateLiteral(Node* node);
Reduction ReduceJSCreateLiteralArrayOrObject(Node* node);
Reduction ReduceJSCreateLiteralRegExp(Node* node);
Reduction ReduceJSCreateFunctionContext(Node* node);
Reduction ReduceJSCreateWithContext(Node* node);
Reduction ReduceJSCreateCatchContext(Node* node);
......@@ -88,6 +89,8 @@ class V8_EXPORT_PRIVATE JSCreateLowering final
Handle<JSObject> boilerplate,
PretenureFlag pretenure,
AllocationSiteUsageContext* site_context);
Node* AllocateLiteralRegExp(Node* effect, Node* control,
Handle<JSRegExp> boilerplate);
Reduction ReduceNewArrayToStubCall(Node* node, Handle<AllocationSite> site);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment