Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(100)

Side by Side Diff: src/compiler/js-typed-lowering.cc

Issue 1109773002: [turbofan] Add SimplifiedOperator::Allocate operator. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Rebased. Created 5 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/compiler/js-typed-lowering.h ('k') | src/compiler/linkage.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 the V8 project authors. All rights reserved. 1 // Copyright 2014 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/code-factory.h" 5 #include "src/code-factory.h"
6 #include "src/compiler/access-builder.h" 6 #include "src/compiler/access-builder.h"
7 #include "src/compiler/js-graph.h" 7 #include "src/compiler/js-graph.h"
8 #include "src/compiler/js-typed-lowering.h" 8 #include "src/compiler/js-typed-lowering.h"
9 #include "src/compiler/linkage.h" 9 #include "src/compiler/linkage.h"
10 #include "src/compiler/node-matchers.h" 10 #include "src/compiler/node-matchers.h"
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
50 } 50 }
51 } 51 }
52 52
53 53
54 Reduction JSTypedLowering::ReplaceEagerly(Node* old, Node* node) { 54 Reduction JSTypedLowering::ReplaceEagerly(Node* old, Node* node) {
55 NodeProperties::ReplaceWithValue(old, node, node); 55 NodeProperties::ReplaceWithValue(old, node, node);
56 return Changed(node); 56 return Changed(node);
57 } 57 }
58 58
59 59
60 // A helper class to construct inline allocations on the simplified operator
61 // level. This keeps track of the effect chain for initial stores on a newly
62 // allocated object and also provides helpers for commonly allocated objects.
63 class AllocationBuilder final {
64 public:
65 AllocationBuilder(JSGraph* jsgraph, SimplifiedOperatorBuilder* simplified,
66 Node* effect, Node* control)
67 : jsgraph_(jsgraph),
68 simplified_(simplified),
69 allocation_(nullptr),
70 effect_(effect),
71 control_(control) {}
72
73 // Primitive allocation of static size.
74 void Allocate(int size) {
75 allocation_ = graph()->NewNode(
76 simplified()->Allocate(), jsgraph()->Constant(size), effect_, control_);
77 effect_ = allocation_;
78 }
79
80 // Primitive store into a field.
81 void Store(const FieldAccess& access, Node* value) {
82 effect_ = graph()->NewNode(simplified()->StoreField(access), allocation_,
83 value, effect_, control_);
84 }
85
86 // Compound allocation of a FixedArray.
87 void AllocateArray(int length, Handle<Map> map) {
88 Allocate(FixedArray::SizeFor(length));
89 Store(AccessBuilder::ForMap(), map);
90 Store(AccessBuilder::ForFixedArrayLength(), jsgraph()->Constant(length));
91 }
92
93 // Compound store of a constant into a field.
94 void Store(const FieldAccess& access, Handle<Object> value) {
95 Store(access, jsgraph()->Constant(value));
96 }
97
98 Node* allocation() const { return allocation_; }
99 Node* effect() const { return effect_; }
100
101 protected:
102 JSGraph* jsgraph() { return jsgraph_; }
103 Graph* graph() { return jsgraph_->graph(); }
104 SimplifiedOperatorBuilder* simplified() { return simplified_; }
105
106 private:
107 JSGraph* const jsgraph_;
108 SimplifiedOperatorBuilder* simplified_;
109 Node* allocation_;
110 Node* effect_;
111 Node* control_;
112 };
113
114
60 // A helper class to simplify the process of reducing a single binop node with a 115 // A helper class to simplify the process of reducing a single binop node with a
61 // JSOperator. This class manages the rewriting of context, control, and effect 116 // JSOperator. This class manages the rewriting of context, control, and effect
62 // dependencies during lowering of a binop and contains numerous helper 117 // dependencies during lowering of a binop and contains numerous helper
63 // functions for matching the types of inputs to an operation. 118 // functions for matching the types of inputs to an operation.
64 class JSBinopReduction final { 119 class JSBinopReduction final {
65 public: 120 public:
66 JSBinopReduction(JSTypedLowering* lowering, Node* node) 121 JSBinopReduction(JSTypedLowering* lowering, Node* node)
67 : lowering_(lowering), node_(node) {} 122 : lowering_(lowering), node_(node) {}
68 123
69 void ConvertPrimitiveInputsToNumber() { 124 void ConvertPrimitiveInputsToNumber() {
(...skipping 942 matching lines...) Expand 10 before | Expand all | Expand 10 after
1012 node->InsertInput(graph()->zone(), 3, jsgraph()->Constant(flags)); 1067 node->InsertInput(graph()->zone(), 3, jsgraph()->Constant(flags));
1013 node->InsertInput(graph()->zone(), 0, stub_code); 1068 node->InsertInput(graph()->zone(), 0, stub_code);
1014 node->set_op(new_op); 1069 node->set_op(new_op);
1015 return Changed(node); 1070 return Changed(node);
1016 } 1071 }
1017 1072
1018 return NoChange(); 1073 return NoChange();
1019 } 1074 }
1020 1075
1021 1076
1077 Reduction JSTypedLowering::ReduceJSCreateWithContext(Node* node) {
1078 DCHECK_EQ(IrOpcode::kJSCreateWithContext, node->opcode());
1079 Node* const input = NodeProperties::GetValueInput(node, 0);
1080 Type* input_type = NodeProperties::GetBounds(input).upper;
1081 if (FLAG_turbo_allocate && input_type->Is(Type::Receiver())) {
1082 // JSCreateWithContext(o:receiver, f)
1083 Node* const effect = NodeProperties::GetEffectInput(node);
1084 Node* const control = NodeProperties::GetControlInput(node);
1085 Node* const closure = NodeProperties::GetValueInput(node, 1);
1086 Node* const context = NodeProperties::GetContextInput(node);
1087 Node* const load = graph()->NewNode(
1088 simplified()->LoadField(
1089 AccessBuilder::ForContextSlot(Context::GLOBAL_OBJECT_INDEX)),
1090 context, effect, control);
1091 AllocationBuilder a(jsgraph(), simplified(), effect, control);
1092 STATIC_ASSERT(Context::MIN_CONTEXT_SLOTS == 4); // Ensure fully covered.
1093 a.AllocateArray(Context::MIN_CONTEXT_SLOTS, factory()->with_context_map());
1094 a.Store(AccessBuilder::ForContextSlot(Context::CLOSURE_INDEX), closure);
1095 a.Store(AccessBuilder::ForContextSlot(Context::PREVIOUS_INDEX), context);
1096 a.Store(AccessBuilder::ForContextSlot(Context::EXTENSION_INDEX), input);
1097 a.Store(AccessBuilder::ForContextSlot(Context::GLOBAL_OBJECT_INDEX), load);
1098 // TODO(mstarzinger): We could mutate {node} into the allocation instead.
1099 NodeProperties::SetBounds(a.allocation(), NodeProperties::GetBounds(node));
1100 NodeProperties::ReplaceWithValue(node, node, a.effect());
1101 node->ReplaceInput(0, a.allocation());
1102 node->ReplaceInput(1, a.effect());
1103 node->set_op(common()->Finish(1));
1104 node->TrimInputCount(2);
1105 return Changed(node);
1106 }
1107 return NoChange();
1108 }
1109
1110
1111 Reduction JSTypedLowering::ReduceJSCreateBlockContext(Node* node) {
1112 DCHECK_EQ(IrOpcode::kJSCreateBlockContext, node->opcode());
1113 Node* const input = NodeProperties::GetValueInput(node, 0);
1114 HeapObjectMatcher<ScopeInfo> minput(input);
1115 DCHECK(minput.HasValue()); // TODO(mstarzinger): Make ScopeInfo static.
1116 int context_length = minput.Value().handle()->ContextLength();
1117 if (FLAG_turbo_allocate && context_length < kBlockContextAllocationLimit) {
1118 // JSCreateBlockContext(s:scope[length < limit], f)
1119 Node* const effect = NodeProperties::GetEffectInput(node);
1120 Node* const control = NodeProperties::GetControlInput(node);
1121 Node* const closure = NodeProperties::GetValueInput(node, 1);
1122 Node* const context = NodeProperties::GetContextInput(node);
1123 Node* const load = graph()->NewNode(
1124 simplified()->LoadField(
1125 AccessBuilder::ForContextSlot(Context::GLOBAL_OBJECT_INDEX)),
1126 context, effect, control);
1127 AllocationBuilder a(jsgraph(), simplified(), effect, control);
1128 STATIC_ASSERT(Context::MIN_CONTEXT_SLOTS == 4); // Ensure fully covered.
1129 a.AllocateArray(context_length, factory()->block_context_map());
1130 a.Store(AccessBuilder::ForContextSlot(Context::CLOSURE_INDEX), closure);
1131 a.Store(AccessBuilder::ForContextSlot(Context::PREVIOUS_INDEX), context);
1132 a.Store(AccessBuilder::ForContextSlot(Context::EXTENSION_INDEX), input);
1133 a.Store(AccessBuilder::ForContextSlot(Context::GLOBAL_OBJECT_INDEX), load);
1134 for (int i = Context::MIN_CONTEXT_SLOTS; i < context_length; ++i) {
1135 a.Store(AccessBuilder::ForContextSlot(i), jsgraph()->TheHoleConstant());
1136 }
1137 // TODO(mstarzinger): We could mutate {node} into the allocation instead.
1138 NodeProperties::SetBounds(a.allocation(), NodeProperties::GetBounds(node));
1139 NodeProperties::ReplaceWithValue(node, node, a.effect());
1140 node->ReplaceInput(0, a.allocation());
1141 node->ReplaceInput(1, a.effect());
1142 node->set_op(common()->Finish(1));
1143 node->TrimInputCount(2);
1144 return Changed(node);
1145 }
1146 return NoChange();
1147 }
1148
1149
1022 Reduction JSTypedLowering::Reduce(Node* node) { 1150 Reduction JSTypedLowering::Reduce(Node* node) {
1023 // Check if the output type is a singleton. In that case we already know the 1151 // Check if the output type is a singleton. In that case we already know the
1024 // result value and can simply replace the node if it's eliminable. 1152 // result value and can simply replace the node if it's eliminable.
1025 if (!NodeProperties::IsConstant(node) && NodeProperties::IsTyped(node) && 1153 if (!NodeProperties::IsConstant(node) && NodeProperties::IsTyped(node) &&
1026 node->op()->HasProperty(Operator::kEliminatable)) { 1154 node->op()->HasProperty(Operator::kEliminatable)) {
1027 Type* upper = NodeProperties::GetBounds(node).upper; 1155 Type* upper = NodeProperties::GetBounds(node).upper;
1028 if (upper->IsConstant()) { 1156 if (upper->IsConstant()) {
1029 Node* replacement = jsgraph()->Constant(upper->AsConstant()->Value()); 1157 Node* replacement = jsgraph()->Constant(upper->AsConstant()->Value());
1030 NodeProperties::ReplaceWithValue(node, replacement); 1158 NodeProperties::ReplaceWithValue(node, replacement);
1031 return Changed(replacement); 1159 return Changed(replacement);
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after
1104 case IrOpcode::kJSLoadContext: 1232 case IrOpcode::kJSLoadContext:
1105 return ReduceJSLoadContext(node); 1233 return ReduceJSLoadContext(node);
1106 case IrOpcode::kJSStoreContext: 1234 case IrOpcode::kJSStoreContext:
1107 return ReduceJSStoreContext(node); 1235 return ReduceJSStoreContext(node);
1108 case IrOpcode::kJSCreateClosure: 1236 case IrOpcode::kJSCreateClosure:
1109 return ReduceJSCreateClosure(node); 1237 return ReduceJSCreateClosure(node);
1110 case IrOpcode::kJSCreateLiteralArray: 1238 case IrOpcode::kJSCreateLiteralArray:
1111 return ReduceJSCreateLiteralArray(node); 1239 return ReduceJSCreateLiteralArray(node);
1112 case IrOpcode::kJSCreateLiteralObject: 1240 case IrOpcode::kJSCreateLiteralObject:
1113 return ReduceJSCreateLiteralObject(node); 1241 return ReduceJSCreateLiteralObject(node);
1242 case IrOpcode::kJSCreateWithContext:
1243 return ReduceJSCreateWithContext(node);
1244 case IrOpcode::kJSCreateBlockContext:
1245 return ReduceJSCreateBlockContext(node);
1114 default: 1246 default:
1115 break; 1247 break;
1116 } 1248 }
1117 return NoChange(); 1249 return NoChange();
1118 } 1250 }
1119 1251
1120 1252
1121 Node* JSTypedLowering::ConvertPrimitiveToNumber(Node* input) { 1253 Node* JSTypedLowering::ConvertPrimitiveToNumber(Node* input) {
1122 DCHECK(NodeProperties::GetBounds(input).upper->Is(Type::PlainPrimitive())); 1254 DCHECK(NodeProperties::GetBounds(input).upper->Is(Type::PlainPrimitive()));
1123 // Avoid inserting too many eager ToNumber() operations. 1255 // Avoid inserting too many eager ToNumber() operations.
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
1178 } 1310 }
1179 1311
1180 1312
1181 MachineOperatorBuilder* JSTypedLowering::machine() const { 1313 MachineOperatorBuilder* JSTypedLowering::machine() const {
1182 return jsgraph()->machine(); 1314 return jsgraph()->machine();
1183 } 1315 }
1184 1316
1185 } // namespace compiler 1317 } // namespace compiler
1186 } // namespace internal 1318 } // namespace internal
1187 } // namespace v8 1319 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/js-typed-lowering.h ('k') | src/compiler/linkage.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698