Line data Source code
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
3 : // found in the LICENSE file.
4 :
5 : #include "src/compiler/common-operator.h"
6 :
7 : #include "src/assembler.h"
8 : #include "src/base/lazy-instance.h"
9 : #include "src/compiler/linkage.h"
10 : #include "src/compiler/node.h"
11 : #include "src/compiler/opcodes.h"
12 : #include "src/compiler/operator.h"
13 : #include "src/handles-inl.h"
14 : #include "src/objects-inl.h"
15 : #include "src/zone/zone.h"
16 :
17 : namespace v8 {
18 : namespace internal {
19 : namespace compiler {
20 :
21 65 : std::ostream& operator<<(std::ostream& os, BranchHint hint) {
22 65 : switch (hint) {
23 : case BranchHint::kNone:
24 31 : return os << "None";
25 : case BranchHint::kTrue:
26 17 : return os << "True";
27 : case BranchHint::kFalse:
28 17 : return os << "False";
29 : }
30 0 : UNREACHABLE();
31 : return os;
32 : }
33 :
34 :
35 5691151 : BranchHint BranchHintOf(const Operator* const op) {
36 : DCHECK_EQ(IrOpcode::kBranch, op->opcode());
37 5691151 : return OpParameter<BranchHint>(op);
38 : }
39 :
40 3472628 : int ValueInputCountOfReturn(Operator const* const op) {
41 : DCHECK(op->opcode() == IrOpcode::kReturn);
42 : // Return nodes have a hidden input at index 0 which we ignore in the value
43 : // input count.
44 3472628 : return op->ValueInputCount() - 1;
45 : }
46 :
47 0 : bool operator==(DeoptimizeParameters lhs, DeoptimizeParameters rhs) {
48 0 : return lhs.kind() == rhs.kind() && lhs.reason() == rhs.reason();
49 : }
50 :
51 0 : bool operator!=(DeoptimizeParameters lhs, DeoptimizeParameters rhs) {
52 0 : return !(lhs == rhs);
53 : }
54 :
55 0 : size_t hash_value(DeoptimizeParameters p) {
56 0 : return base::hash_combine(p.kind(), p.reason());
57 : }
58 :
59 0 : std::ostream& operator<<(std::ostream& os, DeoptimizeParameters p) {
60 0 : return os << p.kind() << ":" << p.reason();
61 : }
62 :
63 1241604 : DeoptimizeParameters const& DeoptimizeParametersOf(Operator const* const op) {
64 : DCHECK(op->opcode() == IrOpcode::kDeoptimize ||
65 : op->opcode() == IrOpcode::kDeoptimizeIf ||
66 : op->opcode() == IrOpcode::kDeoptimizeUnless);
67 1241604 : return OpParameter<DeoptimizeParameters>(op);
68 : }
69 :
70 :
71 1295 : bool operator==(SelectParameters const& lhs, SelectParameters const& rhs) {
72 1295 : return lhs.representation() == rhs.representation() &&
73 0 : lhs.hint() == rhs.hint();
74 : }
75 :
76 :
77 0 : bool operator!=(SelectParameters const& lhs, SelectParameters const& rhs) {
78 0 : return !(lhs == rhs);
79 : }
80 :
81 :
82 31398 : size_t hash_value(SelectParameters const& p) {
83 31398 : return base::hash_combine(p.representation(), p.hint());
84 : }
85 :
86 :
87 0 : std::ostream& operator<<(std::ostream& os, SelectParameters const& p) {
88 0 : return os << p.representation() << "|" << p.hint();
89 : }
90 :
91 :
92 22042 : SelectParameters const& SelectParametersOf(const Operator* const op) {
93 : DCHECK_EQ(IrOpcode::kSelect, op->opcode());
94 22042 : return OpParameter<SelectParameters>(op);
95 : }
96 :
97 9273848 : CallDescriptor const* CallDescriptorOf(const Operator* const op) {
98 : DCHECK(op->opcode() == IrOpcode::kCall ||
99 : op->opcode() == IrOpcode::kTailCall);
100 9273848 : return OpParameter<CallDescriptor const*>(op);
101 : }
102 :
103 829811 : size_t ProjectionIndexOf(const Operator* const op) {
104 : DCHECK_EQ(IrOpcode::kProjection, op->opcode());
105 829811 : return OpParameter<size_t>(op);
106 : }
107 :
108 :
109 1892902 : MachineRepresentation PhiRepresentationOf(const Operator* const op) {
110 : DCHECK_EQ(IrOpcode::kPhi, op->opcode());
111 2367321 : return OpParameter<MachineRepresentation>(op);
112 : }
113 :
114 :
115 6486731 : int ParameterIndexOf(const Operator* const op) {
116 : DCHECK_EQ(IrOpcode::kParameter, op->opcode());
117 6486731 : return OpParameter<ParameterInfo>(op).index();
118 : }
119 :
120 :
121 0 : const ParameterInfo& ParameterInfoOf(const Operator* const op) {
122 : DCHECK_EQ(IrOpcode::kParameter, op->opcode());
123 0 : return OpParameter<ParameterInfo>(op);
124 : }
125 :
126 :
127 7576 : bool operator==(ParameterInfo const& lhs, ParameterInfo const& rhs) {
128 7576 : return lhs.index() == rhs.index();
129 : }
130 :
131 :
132 0 : bool operator!=(ParameterInfo const& lhs, ParameterInfo const& rhs) {
133 0 : return !(lhs == rhs);
134 : }
135 :
136 :
137 3382980 : size_t hash_value(ParameterInfo const& p) { return p.index(); }
138 :
139 :
140 28 : std::ostream& operator<<(std::ostream& os, ParameterInfo const& i) {
141 14 : if (i.debug_name()) os << i.debug_name() << '#';
142 14 : os << i.index();
143 14 : return os;
144 : }
145 :
146 65 : bool operator==(RelocatablePtrConstantInfo const& lhs,
147 65 : RelocatablePtrConstantInfo const& rhs) {
148 65 : return lhs.rmode() == rhs.rmode() && lhs.value() == rhs.value() &&
149 0 : lhs.type() == rhs.type();
150 : }
151 :
152 0 : bool operator!=(RelocatablePtrConstantInfo const& lhs,
153 : RelocatablePtrConstantInfo const& rhs) {
154 0 : return !(lhs == rhs);
155 : }
156 :
157 28614 : size_t hash_value(RelocatablePtrConstantInfo const& p) {
158 28614 : return base::hash_combine(p.value(), p.rmode(), p.type());
159 : }
160 :
161 0 : std::ostream& operator<<(std::ostream& os,
162 0 : RelocatablePtrConstantInfo const& p) {
163 0 : return os << p.value() << "|" << p.rmode() << "|" << p.type();
164 : }
165 :
166 0 : SparseInputMask::InputIterator::InputIterator(
167 : SparseInputMask::BitMaskType bit_mask, Node* parent)
168 18563057 : : bit_mask_(bit_mask), parent_(parent), real_index_(0) {
169 : #if DEBUG
170 : if (bit_mask_ != SparseInputMask::kDenseBitMask) {
171 : DCHECK_EQ(base::bits::CountPopulation(bit_mask_) -
172 : base::bits::CountPopulation(kEndMarker),
173 : parent->InputCount());
174 : }
175 : #endif
176 0 : }
177 :
178 79549127 : void SparseInputMask::InputIterator::Advance() {
179 : DCHECK(!IsEnd());
180 :
181 79549127 : if (IsReal()) {
182 27417703 : ++real_index_;
183 : }
184 79549127 : bit_mask_ >>= 1;
185 79549127 : }
186 :
187 40616684 : Node* SparseInputMask::InputIterator::GetReal() const {
188 : DCHECK(IsReal());
189 81233368 : return parent_->InputAt(real_index_);
190 : }
191 :
192 167306487 : bool SparseInputMask::InputIterator::IsReal() const {
193 455471675 : return bit_mask_ == SparseInputMask::kDenseBitMask ||
194 375922548 : (bit_mask_ & kEntryMask);
195 : }
196 :
197 72034254 : bool SparseInputMask::InputIterator::IsEnd() const {
198 72034254 : return (bit_mask_ == kEndMarker) ||
199 17965277 : (bit_mask_ == SparseInputMask::kDenseBitMask &&
200 89999531 : real_index_ >= parent_->InputCount());
201 : }
202 :
203 0 : int SparseInputMask::CountReal() const {
204 : DCHECK(!IsDense());
205 0 : return base::bits::CountPopulation(bit_mask_) -
206 0 : base::bits::CountPopulation(kEndMarker);
207 : }
208 :
209 18563057 : SparseInputMask::InputIterator SparseInputMask::IterateOverInputs(Node* node) {
210 : DCHECK(IsDense() || CountReal() == node->InputCount());
211 37126114 : return InputIterator(bit_mask_, node);
212 : }
213 :
214 0 : bool operator==(SparseInputMask const& lhs, SparseInputMask const& rhs) {
215 2605511 : return lhs.mask() == rhs.mask();
216 : }
217 :
218 11767952 : bool operator!=(SparseInputMask const& lhs, SparseInputMask const& rhs) {
219 11767952 : return !(lhs == rhs);
220 : }
221 :
222 18117523 : size_t hash_value(SparseInputMask const& p) {
223 18117523 : return base::hash_value(p.mask());
224 : }
225 :
226 0 : std::ostream& operator<<(std::ostream& os, SparseInputMask const& p) {
227 0 : if (p.IsDense()) {
228 0 : return os << "dense";
229 : } else {
230 : SparseInputMask::BitMaskType mask = p.mask();
231 : DCHECK_NE(mask, SparseInputMask::kDenseBitMask);
232 :
233 0 : os << "sparse:";
234 :
235 0 : while (mask != SparseInputMask::kEndMarker) {
236 0 : if (mask & SparseInputMask::kEntryMask) {
237 0 : os << "^";
238 : } else {
239 0 : os << ".";
240 : }
241 0 : mask >>= 1;
242 : }
243 : return os;
244 : }
245 : }
246 :
247 2772861 : bool operator==(TypedStateValueInfo const& lhs,
248 2772861 : TypedStateValueInfo const& rhs) {
249 2772861 : return lhs.machine_types() == rhs.machine_types() &&
250 0 : lhs.sparse_input_mask() == rhs.sparse_input_mask();
251 : }
252 :
253 0 : bool operator!=(TypedStateValueInfo const& lhs,
254 : TypedStateValueInfo const& rhs) {
255 0 : return !(lhs == rhs);
256 : }
257 :
258 22494630 : size_t hash_value(TypedStateValueInfo const& p) {
259 22494585 : return base::hash_combine(p.machine_types(), p.sparse_input_mask());
260 : }
261 :
262 0 : std::ostream& operator<<(std::ostream& os, TypedStateValueInfo const& p) {
263 0 : return os << p.machine_types() << "|" << p.sparse_input_mask();
264 : }
265 :
266 0 : size_t hash_value(RegionObservability observability) {
267 0 : return static_cast<size_t>(observability);
268 : }
269 :
270 0 : std::ostream& operator<<(std::ostream& os, RegionObservability observability) {
271 0 : switch (observability) {
272 : case RegionObservability::kObservable:
273 0 : return os << "observable";
274 : case RegionObservability::kNotObservable:
275 0 : return os << "not-observable";
276 : }
277 0 : UNREACHABLE();
278 : return os;
279 : }
280 :
281 94448 : RegionObservability RegionObservabilityOf(Operator const* op) {
282 : DCHECK_EQ(IrOpcode::kBeginRegion, op->opcode());
283 94448 : return OpParameter<RegionObservability>(op);
284 : }
285 :
286 31591 : Type* TypeGuardTypeOf(Operator const* op) {
287 : DCHECK_EQ(IrOpcode::kTypeGuard, op->opcode());
288 31591 : return OpParameter<Type*>(op);
289 : }
290 :
291 0 : std::ostream& operator<<(std::ostream& os,
292 : const ZoneVector<MachineType>* types) {
293 : // Print all the MachineTypes, separated by commas.
294 : bool first = true;
295 0 : for (MachineType elem : *types) {
296 0 : if (!first) {
297 0 : os << ", ";
298 : }
299 : first = false;
300 0 : os << elem;
301 : }
302 0 : return os;
303 : }
304 :
305 26807 : int OsrValueIndexOf(Operator const* op) {
306 : DCHECK_EQ(IrOpcode::kOsrValue, op->opcode());
307 26807 : return OpParameter<int>(op);
308 : }
309 :
310 0 : size_t hash_value(OsrGuardType type) { return static_cast<size_t>(type); }
311 :
312 0 : std::ostream& operator<<(std::ostream& os, OsrGuardType type) {
313 0 : switch (type) {
314 : case OsrGuardType::kUninitialized:
315 0 : return os << "Uninitialized";
316 : case OsrGuardType::kSignedSmall:
317 0 : return os << "SignedSmall";
318 : case OsrGuardType::kAny:
319 0 : return os << "Any";
320 : }
321 0 : UNREACHABLE();
322 : return os;
323 : }
324 :
325 220911 : OsrGuardType OsrGuardTypeOf(Operator const* op) {
326 : DCHECK_EQ(IrOpcode::kOsrGuard, op->opcode());
327 220911 : return OpParameter<OsrGuardType>(op);
328 : }
329 :
330 34482480 : SparseInputMask SparseInputMaskOf(Operator const* op) {
331 : DCHECK(op->opcode() == IrOpcode::kStateValues ||
332 : op->opcode() == IrOpcode::kTypedStateValues);
333 :
334 34482480 : if (op->opcode() == IrOpcode::kTypedStateValues) {
335 : return OpParameter<TypedStateValueInfo>(op).sparse_input_mask();
336 : }
337 15927191 : return OpParameter<SparseInputMask>(op);
338 : }
339 :
340 13165023 : ZoneVector<MachineType> const* MachineTypesOf(Operator const* op) {
341 : DCHECK(op->opcode() == IrOpcode::kTypedObjectState ||
342 : op->opcode() == IrOpcode::kTypedStateValues);
343 :
344 13165023 : if (op->opcode() == IrOpcode::kTypedStateValues) {
345 13151354 : return OpParameter<TypedStateValueInfo>(op).machine_types();
346 : }
347 13669 : return OpParameter<const ZoneVector<MachineType>*>(op);
348 : }
349 :
350 : #define CACHED_OP_LIST(V) \
351 : V(Dead, Operator::kFoldable, 0, 0, 0, 1, 1, 1) \
352 : V(IfTrue, Operator::kKontrol, 0, 0, 1, 0, 0, 1) \
353 : V(IfFalse, Operator::kKontrol, 0, 0, 1, 0, 0, 1) \
354 : V(IfSuccess, Operator::kKontrol, 0, 0, 1, 0, 0, 1) \
355 : V(IfException, Operator::kKontrol, 0, 1, 1, 1, 1, 1) \
356 : V(IfDefault, Operator::kKontrol, 0, 0, 1, 0, 0, 1) \
357 : V(Throw, Operator::kKontrol, 0, 1, 1, 0, 0, 1) \
358 : V(Terminate, Operator::kKontrol, 0, 1, 1, 0, 0, 1) \
359 : V(OsrNormalEntry, Operator::kFoldable, 0, 1, 1, 0, 1, 1) \
360 : V(OsrLoopEntry, Operator::kFoldable | Operator::kNoThrow, 0, 1, 1, 0, 1, 1) \
361 : V(LoopExit, Operator::kKontrol, 0, 0, 2, 0, 0, 1) \
362 : V(LoopExitValue, Operator::kPure, 1, 0, 1, 1, 0, 0) \
363 : V(LoopExitEffect, Operator::kNoThrow, 0, 1, 1, 0, 1, 0) \
364 : V(Checkpoint, Operator::kKontrol, 0, 1, 1, 0, 1, 0) \
365 : V(FinishRegion, Operator::kKontrol, 1, 1, 0, 1, 1, 0) \
366 : V(Retain, Operator::kKontrol, 1, 1, 0, 0, 1, 0)
367 :
368 : #define CACHED_RETURN_LIST(V) \
369 : V(1) \
370 : V(2) \
371 : V(3) \
372 : V(4)
373 :
374 : #define CACHED_END_LIST(V) \
375 : V(1) \
376 : V(2) \
377 : V(3) \
378 : V(4) \
379 : V(5) \
380 : V(6) \
381 : V(7) \
382 : V(8)
383 :
384 :
385 : #define CACHED_EFFECT_PHI_LIST(V) \
386 : V(1) \
387 : V(2) \
388 : V(3) \
389 : V(4) \
390 : V(5) \
391 : V(6)
392 :
393 : #define CACHED_INDUCTION_VARIABLE_PHI_LIST(V) \
394 : V(4) \
395 : V(5) \
396 : V(6) \
397 : V(7)
398 :
399 : #define CACHED_LOOP_LIST(V) \
400 : V(1) \
401 : V(2)
402 :
403 :
404 : #define CACHED_MERGE_LIST(V) \
405 : V(1) \
406 : V(2) \
407 : V(3) \
408 : V(4) \
409 : V(5) \
410 : V(6) \
411 : V(7) \
412 : V(8)
413 :
414 : #define CACHED_DEOPTIMIZE_LIST(V) \
415 : V(Eager, MinusZero) \
416 : V(Eager, NoReason) \
417 : V(Eager, WrongMap) \
418 : V(Soft, InsufficientTypeFeedbackForGenericKeyedAccess) \
419 : V(Soft, InsufficientTypeFeedbackForGenericNamedAccess)
420 :
421 : #define CACHED_DEOPTIMIZE_IF_LIST(V) \
422 : V(Eager, DivisionByZero) \
423 : V(Eager, Hole) \
424 : V(Eager, MinusZero) \
425 : V(Eager, Overflow) \
426 : V(Eager, Smi)
427 :
428 : #define CACHED_DEOPTIMIZE_UNLESS_LIST(V) \
429 : V(Eager, LostPrecision) \
430 : V(Eager, LostPrecisionOrNaN) \
431 : V(Eager, NoReason) \
432 : V(Eager, NotAHeapNumber) \
433 : V(Eager, NotANumberOrOddball) \
434 : V(Eager, NotASmi) \
435 : V(Eager, OutOfBounds) \
436 : V(Eager, WrongInstanceType) \
437 : V(Eager, WrongMap)
438 :
439 : #define CACHED_TRAP_IF_LIST(V) \
440 : V(TrapDivUnrepresentable) \
441 : V(TrapFloatUnrepresentable)
442 :
443 : // The reason for a trap.
444 : #define CACHED_TRAP_UNLESS_LIST(V) \
445 : V(TrapUnreachable) \
446 : V(TrapMemOutOfBounds) \
447 : V(TrapDivByZero) \
448 : V(TrapDivUnrepresentable) \
449 : V(TrapRemByZero) \
450 : V(TrapFloatUnrepresentable) \
451 : V(TrapFuncInvalid) \
452 : V(TrapFuncSigMismatch)
453 :
454 : #define CACHED_PARAMETER_LIST(V) \
455 : V(0) \
456 : V(1) \
457 : V(2) \
458 : V(3) \
459 : V(4) \
460 : V(5) \
461 : V(6)
462 :
463 :
464 : #define CACHED_PHI_LIST(V) \
465 : V(kTagged, 1) \
466 : V(kTagged, 2) \
467 : V(kTagged, 3) \
468 : V(kTagged, 4) \
469 : V(kTagged, 5) \
470 : V(kTagged, 6) \
471 : V(kBit, 2) \
472 : V(kFloat64, 2) \
473 : V(kWord32, 2)
474 :
475 :
476 : #define CACHED_PROJECTION_LIST(V) \
477 : V(0) \
478 : V(1)
479 :
480 :
481 : #define CACHED_STATE_VALUES_LIST(V) \
482 : V(0) \
483 : V(1) \
484 : V(2) \
485 : V(3) \
486 : V(4) \
487 : V(5) \
488 : V(6) \
489 : V(7) \
490 : V(8) \
491 : V(10) \
492 : V(11) \
493 : V(12) \
494 : V(13) \
495 : V(14)
496 :
497 :
498 35479 : struct CommonOperatorGlobalCache final {
499 : #define CACHED(Name, properties, value_input_count, effect_input_count, \
500 : control_input_count, value_output_count, effect_output_count, \
501 : control_output_count) \
502 : struct Name##Operator final : public Operator { \
503 : Name##Operator() \
504 : : Operator(IrOpcode::k##Name, properties, #Name, value_input_count, \
505 : effect_input_count, control_input_count, \
506 : value_output_count, effect_output_count, \
507 : control_output_count) {} \
508 : }; \
509 : Name##Operator k##Name##Operator;
510 1099849 : CACHED_OP_LIST(CACHED)
511 : #undef CACHED
512 :
513 : template <size_t kInputCount>
514 0 : struct EndOperator final : public Operator {
515 283832 : EndOperator()
516 : : Operator( // --
517 : IrOpcode::kEnd, Operator::kKontrol, // opcode
518 : "End", // name
519 283832 : 0, 0, kInputCount, 0, 0, 0) {} // counts
520 : };
521 : #define CACHED_END(input_count) \
522 : EndOperator<input_count> kEnd##input_count##Operator;
523 : CACHED_END_LIST(CACHED_END)
524 : #undef CACHED_END
525 :
526 : template <size_t kValueInputCount>
527 0 : struct ReturnOperator final : public Operator {
528 141916 : ReturnOperator()
529 : : Operator( // --
530 : IrOpcode::kReturn, Operator::kNoThrow, // opcode
531 : "Return", // name
532 141916 : kValueInputCount + 1, 1, 1, 0, 0, 1) {} // counts
533 : };
534 : #define CACHED_RETURN(value_input_count) \
535 : ReturnOperator<value_input_count> kReturn##value_input_count##Operator;
536 : CACHED_RETURN_LIST(CACHED_RETURN)
537 : #undef CACHED_RETURN
538 :
539 : template <BranchHint kBranchHint>
540 0 : struct BranchOperator final : public Operator1<BranchHint> {
541 106437 : BranchOperator()
542 : : Operator1<BranchHint>( // --
543 : IrOpcode::kBranch, Operator::kKontrol, // opcode
544 : "Branch", // name
545 : 1, 0, 1, 0, 0, 2, // counts
546 106437 : kBranchHint) {} // parameter
547 : };
548 : BranchOperator<BranchHint::kNone> kBranchNoneOperator;
549 : BranchOperator<BranchHint::kTrue> kBranchTrueOperator;
550 : BranchOperator<BranchHint::kFalse> kBranchFalseOperator;
551 :
552 : template <int kEffectInputCount>
553 0 : struct EffectPhiOperator final : public Operator {
554 212874 : EffectPhiOperator()
555 : : Operator( // --
556 : IrOpcode::kEffectPhi, Operator::kKontrol, // opcode
557 : "EffectPhi", // name
558 212874 : 0, kEffectInputCount, 1, 0, 1, 0) {} // counts
559 : };
560 : #define CACHED_EFFECT_PHI(input_count) \
561 : EffectPhiOperator<input_count> kEffectPhi##input_count##Operator;
562 : CACHED_EFFECT_PHI_LIST(CACHED_EFFECT_PHI)
563 : #undef CACHED_EFFECT_PHI
564 :
565 : template <RegionObservability kRegionObservability>
566 0 : struct BeginRegionOperator final : public Operator1<RegionObservability> {
567 70958 : BeginRegionOperator()
568 : : Operator1<RegionObservability>( // --
569 : IrOpcode::kBeginRegion, Operator::kKontrol, // opcode
570 : "BeginRegion", // name
571 : 0, 1, 0, 0, 1, 0, // counts
572 70958 : kRegionObservability) {} // parameter
573 : };
574 : BeginRegionOperator<RegionObservability::kObservable>
575 : kBeginRegionObservableOperator;
576 : BeginRegionOperator<RegionObservability::kNotObservable>
577 : kBeginRegionNotObservableOperator;
578 :
579 : template <size_t kInputCount>
580 0 : struct LoopOperator final : public Operator {
581 70958 : LoopOperator()
582 : : Operator( // --
583 : IrOpcode::kLoop, Operator::kKontrol, // opcode
584 : "Loop", // name
585 70958 : 0, 0, kInputCount, 0, 0, 1) {} // counts
586 : };
587 : #define CACHED_LOOP(input_count) \
588 : LoopOperator<input_count> kLoop##input_count##Operator;
589 : CACHED_LOOP_LIST(CACHED_LOOP)
590 : #undef CACHED_LOOP
591 :
592 : template <size_t kInputCount>
593 0 : struct MergeOperator final : public Operator {
594 283832 : MergeOperator()
595 : : Operator( // --
596 : IrOpcode::kMerge, Operator::kKontrol, // opcode
597 : "Merge", // name
598 283832 : 0, 0, kInputCount, 0, 0, 1) {} // counts
599 : };
600 : #define CACHED_MERGE(input_count) \
601 : MergeOperator<input_count> kMerge##input_count##Operator;
602 : CACHED_MERGE_LIST(CACHED_MERGE)
603 : #undef CACHED_MERGE
604 :
605 : template <DeoptimizeKind kKind, DeoptimizeReason kReason>
606 0 : struct DeoptimizeOperator final : public Operator1<DeoptimizeParameters> {
607 177395 : DeoptimizeOperator()
608 : : Operator1<DeoptimizeParameters>( // --
609 : IrOpcode::kDeoptimize, // opcode
610 : Operator::kFoldable | Operator::kNoThrow, // properties
611 : "Deoptimize", // name
612 : 1, 1, 1, 0, 0, 1, // counts
613 177395 : DeoptimizeParameters(kKind, kReason)) {} // parameter
614 : };
615 : #define CACHED_DEOPTIMIZE(Kind, Reason) \
616 : DeoptimizeOperator<DeoptimizeKind::k##Kind, DeoptimizeReason::k##Reason> \
617 : kDeoptimize##Kind##Reason##Operator;
618 : CACHED_DEOPTIMIZE_LIST(CACHED_DEOPTIMIZE)
619 : #undef CACHED_DEOPTIMIZE
620 :
621 : template <DeoptimizeKind kKind, DeoptimizeReason kReason>
622 0 : struct DeoptimizeIfOperator final : public Operator1<DeoptimizeParameters> {
623 177395 : DeoptimizeIfOperator()
624 : : Operator1<DeoptimizeParameters>( // --
625 : IrOpcode::kDeoptimizeIf, // opcode
626 : Operator::kFoldable | Operator::kNoThrow, // properties
627 : "DeoptimizeIf", // name
628 : 2, 1, 1, 0, 1, 1, // counts
629 177395 : DeoptimizeParameters(kKind, kReason)) {} // parameter
630 : };
631 : #define CACHED_DEOPTIMIZE_IF(Kind, Reason) \
632 : DeoptimizeIfOperator<DeoptimizeKind::k##Kind, DeoptimizeReason::k##Reason> \
633 : kDeoptimizeIf##Kind##Reason##Operator;
634 : CACHED_DEOPTIMIZE_IF_LIST(CACHED_DEOPTIMIZE_IF)
635 : #undef CACHED_DEOPTIMIZE_IF
636 :
637 : template <DeoptimizeKind kKind, DeoptimizeReason kReason>
638 0 : struct DeoptimizeUnlessOperator final
639 : : public Operator1<DeoptimizeParameters> {
640 319311 : DeoptimizeUnlessOperator()
641 : : Operator1<DeoptimizeParameters>( // --
642 : IrOpcode::kDeoptimizeUnless, // opcode
643 : Operator::kFoldable | Operator::kNoThrow, // properties
644 : "DeoptimizeUnless", // name
645 : 2, 1, 1, 0, 1, 1, // counts
646 319311 : DeoptimizeParameters(kKind, kReason)) {} // parameter
647 : };
648 : #define CACHED_DEOPTIMIZE_UNLESS(Kind, Reason) \
649 : DeoptimizeUnlessOperator<DeoptimizeKind::k##Kind, \
650 : DeoptimizeReason::k##Reason> \
651 : kDeoptimizeUnless##Kind##Reason##Operator;
652 : CACHED_DEOPTIMIZE_UNLESS_LIST(CACHED_DEOPTIMIZE_UNLESS)
653 : #undef CACHED_DEOPTIMIZE_UNLESS
654 :
655 : template <int32_t trap_id>
656 0 : struct TrapIfOperator final : public Operator1<int32_t> {
657 70958 : TrapIfOperator()
658 : : Operator1<int32_t>( // --
659 : IrOpcode::kTrapIf, // opcode
660 : Operator::kFoldable | Operator::kNoThrow, // properties
661 : "TrapIf", // name
662 : 1, 1, 1, 0, 0, 1, // counts
663 70958 : trap_id) {} // parameter
664 : };
665 : #define CACHED_TRAP_IF(Trap) \
666 : TrapIfOperator<static_cast<int32_t>(Builtins::kThrowWasm##Trap)> \
667 : kTrapIf##Trap##Operator;
668 : CACHED_TRAP_IF_LIST(CACHED_TRAP_IF)
669 : #undef CACHED_TRAP_IF
670 :
671 : template <int32_t trap_id>
672 0 : struct TrapUnlessOperator final : public Operator1<int32_t> {
673 283832 : TrapUnlessOperator()
674 : : Operator1<int32_t>( // --
675 : IrOpcode::kTrapUnless, // opcode
676 : Operator::kFoldable | Operator::kNoThrow, // properties
677 : "TrapUnless", // name
678 : 1, 1, 1, 0, 0, 1, // counts
679 283832 : trap_id) {} // parameter
680 : };
681 : #define CACHED_TRAP_UNLESS(Trap) \
682 : TrapUnlessOperator<static_cast<int32_t>(Builtins::kThrowWasm##Trap)> \
683 : kTrapUnless##Trap##Operator;
684 : CACHED_TRAP_UNLESS_LIST(CACHED_TRAP_UNLESS)
685 : #undef CACHED_TRAP_UNLESS
686 :
687 : template <MachineRepresentation kRep, int kInputCount>
688 0 : struct PhiOperator final : public Operator1<MachineRepresentation> {
689 319311 : PhiOperator()
690 : : Operator1<MachineRepresentation>( //--
691 : IrOpcode::kPhi, Operator::kPure, // opcode
692 : "Phi", // name
693 : kInputCount, 0, 1, 1, 0, 0, // counts
694 319311 : kRep) {} // parameter
695 : };
696 : #define CACHED_PHI(rep, input_count) \
697 : PhiOperator<MachineRepresentation::rep, input_count> \
698 : kPhi##rep##input_count##Operator;
699 : CACHED_PHI_LIST(CACHED_PHI)
700 : #undef CACHED_PHI
701 :
702 : template <int kInputCount>
703 0 : struct InductionVariablePhiOperator final : public Operator {
704 141916 : InductionVariablePhiOperator()
705 : : Operator( //--
706 : IrOpcode::kInductionVariablePhi, Operator::kPure, // opcode
707 : "InductionVariablePhi", // name
708 141916 : kInputCount, 0, 1, 1, 0, 0) {} // counts
709 : };
710 : #define CACHED_INDUCTION_VARIABLE_PHI(input_count) \
711 : InductionVariablePhiOperator<input_count> \
712 : kInductionVariablePhi##input_count##Operator;
713 : CACHED_INDUCTION_VARIABLE_PHI_LIST(CACHED_INDUCTION_VARIABLE_PHI)
714 : #undef CACHED_INDUCTION_VARIABLE_PHI
715 :
716 : template <int kIndex>
717 0 : struct ParameterOperator final : public Operator1<ParameterInfo> {
718 248353 : ParameterOperator()
719 : : Operator1<ParameterInfo>( // --
720 : IrOpcode::kParameter, Operator::kPure, // opcode
721 : "Parameter", // name
722 : 1, 0, 0, 1, 0, 0, // counts,
723 248353 : ParameterInfo(kIndex, nullptr)) {} // parameter and name
724 : };
725 : #define CACHED_PARAMETER(index) \
726 : ParameterOperator<index> kParameter##index##Operator;
727 : CACHED_PARAMETER_LIST(CACHED_PARAMETER)
728 : #undef CACHED_PARAMETER
729 :
730 : template <size_t kIndex>
731 0 : struct ProjectionOperator final : public Operator1<size_t> {
732 70958 : ProjectionOperator()
733 : : Operator1<size_t>( // --
734 : IrOpcode::kProjection, // opcode
735 : Operator::kPure, // flags
736 : "Projection", // name
737 : 1, 0, 1, 1, 0, 0, // counts,
738 70958 : kIndex) {} // parameter
739 : };
740 : #define CACHED_PROJECTION(index) \
741 : ProjectionOperator<index> kProjection##index##Operator;
742 : CACHED_PROJECTION_LIST(CACHED_PROJECTION)
743 : #undef CACHED_PROJECTION
744 :
745 : template <int kInputCount>
746 0 : struct StateValuesOperator final : public Operator1<SparseInputMask> {
747 496706 : StateValuesOperator()
748 : : Operator1<SparseInputMask>( // --
749 : IrOpcode::kStateValues, // opcode
750 : Operator::kPure, // flags
751 : "StateValues", // name
752 : kInputCount, 0, 0, 1, 0, 0, // counts
753 496706 : SparseInputMask::Dense()) {} // parameter
754 : };
755 : #define CACHED_STATE_VALUES(input_count) \
756 : StateValuesOperator<input_count> kStateValues##input_count##Operator;
757 : CACHED_STATE_VALUES_LIST(CACHED_STATE_VALUES)
758 : #undef CACHED_STATE_VALUES
759 : };
760 :
761 :
762 : static base::LazyInstance<CommonOperatorGlobalCache>::type kCache =
763 : LAZY_INSTANCE_INITIALIZER;
764 :
765 :
766 1224741 : CommonOperatorBuilder::CommonOperatorBuilder(Zone* zone)
767 1224741 : : cache_(kCache.Get()), zone_(zone) {}
768 :
769 :
770 : #define CACHED(Name, properties, value_input_count, effect_input_count, \
771 : control_input_count, value_output_count, effect_output_count, \
772 : control_output_count) \
773 : const Operator* CommonOperatorBuilder::Name() { \
774 : return &cache_.k##Name##Operator; \
775 : }
776 20185502 : CACHED_OP_LIST(CACHED)
777 : #undef CACHED
778 :
779 :
780 1907016 : const Operator* CommonOperatorBuilder::End(size_t control_input_count) {
781 1455443 : switch (control_input_count) {
782 : #define CACHED_END(input_count) \
783 : case input_count: \
784 : return &cache_.kEnd##input_count##Operator;
785 760375 : CACHED_END_LIST(CACHED_END)
786 : #undef CACHED_END
787 : default:
788 : break;
789 : }
790 : // Uncached.
791 : return new (zone()) Operator( //--
792 : IrOpcode::kEnd, Operator::kKontrol, // opcode
793 : "End", // name
794 451573 : 0, 0, control_input_count, 0, 0, 0); // counts
795 : }
796 :
797 1417203 : const Operator* CommonOperatorBuilder::Return(int value_input_count) {
798 1403278 : switch (value_input_count) {
799 : #define CACHED_RETURN(input_count) \
800 : case input_count: \
801 : return &cache_.kReturn##input_count##Operator;
802 1388324 : CACHED_RETURN_LIST(CACHED_RETURN)
803 : #undef CACHED_RETURN
804 : default:
805 : break;
806 : }
807 : // Uncached.
808 : return new (zone()) Operator( //--
809 : IrOpcode::kReturn, Operator::kNoThrow, // opcode
810 : "Return", // name
811 13922 : value_input_count + 1, 1, 1, 0, 0, 1); // counts
812 : }
813 :
814 :
815 4625124 : const Operator* CommonOperatorBuilder::Branch(BranchHint hint) {
816 4625124 : switch (hint) {
817 : case BranchHint::kNone:
818 3471247 : return &cache_.kBranchNoneOperator;
819 : case BranchHint::kTrue:
820 719207 : return &cache_.kBranchTrueOperator;
821 : case BranchHint::kFalse:
822 434670 : return &cache_.kBranchFalseOperator;
823 : }
824 0 : UNREACHABLE();
825 : return nullptr;
826 : }
827 :
828 29196 : const Operator* CommonOperatorBuilder::Deoptimize(DeoptimizeKind kind,
829 61 : DeoptimizeReason reason) {
830 : #define CACHED_DEOPTIMIZE(Kind, Reason) \
831 : if (kind == DeoptimizeKind::k##Kind && \
832 : reason == DeoptimizeReason::k##Reason) { \
833 : return &cache_.kDeoptimize##Kind##Reason##Operator; \
834 : }
835 29196 : CACHED_DEOPTIMIZE_LIST(CACHED_DEOPTIMIZE)
836 : #undef CACHED_DEOPTIMIZE
837 : // Uncached
838 : DeoptimizeParameters parameter(kind, reason);
839 : return new (zone()) Operator1<DeoptimizeParameters>( // --
840 : IrOpcode::kDeoptimize, // opcodes
841 : Operator::kFoldable | Operator::kNoThrow, // properties
842 : "Deoptimize", // name
843 : 1, 1, 1, 0, 0, 1, // counts
844 : parameter); // parameter
845 : }
846 :
847 102499 : const Operator* CommonOperatorBuilder::DeoptimizeIf(DeoptimizeKind kind,
848 1613 : DeoptimizeReason reason) {
849 : #define CACHED_DEOPTIMIZE_IF(Kind, Reason) \
850 : if (kind == DeoptimizeKind::k##Kind && \
851 : reason == DeoptimizeReason::k##Reason) { \
852 : return &cache_.kDeoptimizeIf##Kind##Reason##Operator; \
853 : }
854 102499 : CACHED_DEOPTIMIZE_IF_LIST(CACHED_DEOPTIMIZE_IF)
855 : #undef CACHED_DEOPTIMIZE_IF
856 : // Uncached
857 : DeoptimizeParameters parameter(kind, reason);
858 : return new (zone()) Operator1<DeoptimizeParameters>( // --
859 : IrOpcode::kDeoptimizeIf, // opcode
860 : Operator::kFoldable | Operator::kNoThrow, // properties
861 : "DeoptimizeIf", // name
862 : 2, 1, 1, 0, 1, 1, // counts
863 : parameter); // parameter
864 : }
865 :
866 192077 : const Operator* CommonOperatorBuilder::DeoptimizeUnless(
867 473 : DeoptimizeKind kind, DeoptimizeReason reason) {
868 : #define CACHED_DEOPTIMIZE_UNLESS(Kind, Reason) \
869 : if (kind == DeoptimizeKind::k##Kind && \
870 : reason == DeoptimizeReason::k##Reason) { \
871 : return &cache_.kDeoptimizeUnless##Kind##Reason##Operator; \
872 : }
873 192077 : CACHED_DEOPTIMIZE_UNLESS_LIST(CACHED_DEOPTIMIZE_UNLESS)
874 : #undef CACHED_DEOPTIMIZE_UNLESS
875 : // Uncached
876 : DeoptimizeParameters parameter(kind, reason);
877 : return new (zone()) Operator1<DeoptimizeParameters>( // --
878 : IrOpcode::kDeoptimizeUnless, // opcode
879 : Operator::kFoldable | Operator::kNoThrow, // properties
880 : "DeoptimizeUnless", // name
881 : 2, 1, 1, 0, 1, 1, // counts
882 : parameter); // parameter
883 : }
884 :
885 1596 : const Operator* CommonOperatorBuilder::TrapIf(int32_t trap_id) {
886 882 : switch (trap_id) {
887 : #define CACHED_TRAP_IF(Trap) \
888 : case Builtins::kThrowWasm##Trap: \
889 : return &cache_.kTrapIf##Trap##Operator;
890 16 : CACHED_TRAP_IF_LIST(CACHED_TRAP_IF)
891 : #undef CACHED_TRAP_IF
892 : default:
893 : break;
894 : }
895 : // Uncached
896 : return new (zone()) Operator1<int>( // --
897 : IrOpcode::kTrapIf, // opcode
898 : Operator::kFoldable | Operator::kNoThrow, // properties
899 : "TrapIf", // name
900 : 1, 1, 1, 0, 0, 1, // counts
901 : trap_id); // parameter
902 : }
903 :
904 21100 : const Operator* CommonOperatorBuilder::TrapUnless(int32_t trap_id) {
905 15716 : switch (trap_id) {
906 : #define CACHED_TRAP_UNLESS(Trap) \
907 : case Builtins::kThrowWasm##Trap: \
908 : return &cache_.kTrapUnless##Trap##Operator;
909 383 : CACHED_TRAP_UNLESS_LIST(CACHED_TRAP_UNLESS)
910 : #undef CACHED_TRAP_UNLESS
911 : default:
912 : break;
913 : }
914 : // Uncached
915 : return new (zone()) Operator1<int>( // --
916 : IrOpcode::kTrapUnless, // opcode
917 : Operator::kFoldable | Operator::kNoThrow, // properties
918 : "TrapUnless", // name
919 : 1, 1, 1, 0, 0, 1, // counts
920 : trap_id); // parameter
921 : }
922 :
923 46334 : const Operator* CommonOperatorBuilder::Switch(size_t control_output_count) {
924 : return new (zone()) Operator( // --
925 : IrOpcode::kSwitch, Operator::kKontrol, // opcode
926 : "Switch", // name
927 23167 : 1, 0, 1, 0, 0, control_output_count); // counts
928 : }
929 :
930 :
931 145292 : const Operator* CommonOperatorBuilder::IfValue(int32_t index) {
932 : return new (zone()) Operator1<int32_t>( // --
933 : IrOpcode::kIfValue, Operator::kKontrol, // opcode
934 : "IfValue", // name
935 : 0, 0, 1, 0, 0, 1, // counts
936 145292 : index); // parameter
937 : }
938 :
939 :
940 2386576 : const Operator* CommonOperatorBuilder::Start(int value_output_count) {
941 : return new (zone()) Operator( // --
942 2386576 : IrOpcode::kStart, Operator::kFoldable | Operator::kNoThrow, // opcode
943 : "Start", // name
944 2386577 : 0, 0, 0, value_output_count, 1, 1); // counts
945 : }
946 :
947 :
948 818515 : const Operator* CommonOperatorBuilder::Loop(int control_input_count) {
949 811688 : switch (control_input_count) {
950 : #define CACHED_LOOP(input_count) \
951 : case input_count: \
952 : return &cache_.kLoop##input_count##Operator;
953 55507 : CACHED_LOOP_LIST(CACHED_LOOP)
954 : #undef CACHED_LOOP
955 : default:
956 : break;
957 : }
958 : // Uncached.
959 : return new (zone()) Operator( // --
960 : IrOpcode::kLoop, Operator::kKontrol, // opcode
961 : "Loop", // name
962 6827 : 0, 0, control_input_count, 0, 0, 1); // counts
963 : }
964 :
965 :
966 3685722 : const Operator* CommonOperatorBuilder::Merge(int control_input_count) {
967 3503680 : switch (control_input_count) {
968 : #define CACHED_MERGE(input_count) \
969 : case input_count: \
970 : return &cache_.kMerge##input_count##Operator;
971 908734 : CACHED_MERGE_LIST(CACHED_MERGE)
972 : #undef CACHED_MERGE
973 : default:
974 : break;
975 : }
976 : // Uncached.
977 : return new (zone()) Operator( // --
978 : IrOpcode::kMerge, Operator::kKontrol, // opcode
979 : "Merge", // name
980 182042 : 0, 0, control_input_count, 0, 0, 1); // counts
981 : }
982 :
983 :
984 3046395 : const Operator* CommonOperatorBuilder::Parameter(int index,
985 1539501 : const char* debug_name) {
986 3046395 : if (!debug_name) {
987 1711034 : switch (index) {
988 : #define CACHED_PARAMETER(index) \
989 : case index: \
990 : return &cache_.kParameter##index##Operator;
991 575202 : CACHED_PARAMETER_LIST(CACHED_PARAMETER)
992 : #undef CACHED_PARAMETER
993 : default:
994 : break;
995 : }
996 : }
997 : // Uncached.
998 : return new (zone()) Operator1<ParameterInfo>( // --
999 : IrOpcode::kParameter, Operator::kPure, // opcode
1000 : "Parameter", // name
1001 : 1, 0, 0, 1, 0, 0, // counts
1002 : ParameterInfo(index, debug_name)); // parameter info
1003 : }
1004 :
1005 54757 : const Operator* CommonOperatorBuilder::OsrValue(int index) {
1006 : return new (zone()) Operator1<int>( // --
1007 : IrOpcode::kOsrValue, Operator::kNoProperties, // opcode
1008 : "OsrValue", // name
1009 : 0, 0, 1, 1, 0, 0, // counts
1010 54757 : index); // parameter
1011 : }
1012 :
1013 60570 : const Operator* CommonOperatorBuilder::OsrGuard(OsrGuardType type) {
1014 : return new (zone()) Operator1<OsrGuardType>( // --
1015 : IrOpcode::kOsrGuard, Operator::kNoThrow, // opcode
1016 : "OsrGuard", // name
1017 : 1, 1, 1, 1, 1, 0, // counts
1018 60570 : type); // parameter
1019 : }
1020 :
1021 7621994 : const Operator* CommonOperatorBuilder::Int32Constant(int32_t value) {
1022 : return new (zone()) Operator1<int32_t>( // --
1023 : IrOpcode::kInt32Constant, Operator::kPure, // opcode
1024 : "Int32Constant", // name
1025 : 0, 0, 0, 1, 0, 0, // counts
1026 7622080 : value); // parameter
1027 : }
1028 :
1029 :
1030 7631144 : const Operator* CommonOperatorBuilder::Int64Constant(int64_t value) {
1031 : return new (zone()) Operator1<int64_t>( // --
1032 : IrOpcode::kInt64Constant, Operator::kPure, // opcode
1033 : "Int64Constant", // name
1034 : 0, 0, 0, 1, 0, 0, // counts
1035 7631167 : value); // parameter
1036 : }
1037 :
1038 :
1039 576538 : const Operator* CommonOperatorBuilder::Float32Constant(volatile float value) {
1040 : return new (zone()) Operator1<float>( // --
1041 : IrOpcode::kFloat32Constant, Operator::kPure, // opcode
1042 : "Float32Constant", // name
1043 : 0, 0, 0, 1, 0, 0, // counts
1044 576538 : value); // parameter
1045 : }
1046 :
1047 :
1048 671702 : const Operator* CommonOperatorBuilder::Float64Constant(volatile double value) {
1049 : return new (zone()) Operator1<double>( // --
1050 : IrOpcode::kFloat64Constant, Operator::kPure, // opcode
1051 : "Float64Constant", // name
1052 : 0, 0, 0, 1, 0, 0, // counts
1053 671702 : value); // parameter
1054 : }
1055 :
1056 :
1057 1551949 : const Operator* CommonOperatorBuilder::ExternalConstant(
1058 1551949 : const ExternalReference& value) {
1059 : return new (zone()) Operator1<ExternalReference>( // --
1060 : IrOpcode::kExternalConstant, Operator::kPure, // opcode
1061 : "ExternalConstant", // name
1062 : 0, 0, 0, 1, 0, 0, // counts
1063 3103916 : value); // parameter
1064 : }
1065 :
1066 :
1067 8461360 : const Operator* CommonOperatorBuilder::NumberConstant(volatile double value) {
1068 : return new (zone()) Operator1<double>( // --
1069 : IrOpcode::kNumberConstant, Operator::kPure, // opcode
1070 : "NumberConstant", // name
1071 : 0, 0, 0, 1, 0, 0, // counts
1072 8461348 : value); // parameter
1073 : }
1074 :
1075 1398 : const Operator* CommonOperatorBuilder::PointerConstant(intptr_t value) {
1076 : return new (zone()) Operator1<intptr_t>( // --
1077 : IrOpcode::kPointerConstant, Operator::kPure, // opcode
1078 : "PointerConstant", // name
1079 : 0, 0, 0, 1, 0, 0, // counts
1080 1398 : value); // parameter
1081 : }
1082 :
1083 9873423 : const Operator* CommonOperatorBuilder::HeapConstant(
1084 9873423 : const Handle<HeapObject>& value) {
1085 : return new (zone()) Operator1<Handle<HeapObject>>( // --
1086 : IrOpcode::kHeapConstant, Operator::kPure, // opcode
1087 : "HeapConstant", // name
1088 : 0, 0, 0, 1, 0, 0, // counts
1089 19746835 : value); // parameter
1090 : }
1091 :
1092 10398 : const Operator* CommonOperatorBuilder::RelocatableInt32Constant(
1093 10398 : int32_t value, RelocInfo::Mode rmode) {
1094 : return new (zone()) Operator1<RelocatablePtrConstantInfo>( // --
1095 : IrOpcode::kRelocatableInt32Constant, Operator::kPure, // opcode
1096 : "RelocatableInt32Constant", // name
1097 : 0, 0, 0, 1, 0, 0, // counts
1098 10399 : RelocatablePtrConstantInfo(value, rmode)); // parameter
1099 : }
1100 :
1101 15463 : const Operator* CommonOperatorBuilder::RelocatableInt64Constant(
1102 15463 : int64_t value, RelocInfo::Mode rmode) {
1103 : return new (zone()) Operator1<RelocatablePtrConstantInfo>( // --
1104 : IrOpcode::kRelocatableInt64Constant, Operator::kPure, // opcode
1105 : "RelocatableInt64Constant", // name
1106 : 0, 0, 0, 1, 0, 0, // counts
1107 15463 : RelocatablePtrConstantInfo(value, rmode)); // parameter
1108 : }
1109 :
1110 28940 : const Operator* CommonOperatorBuilder::Select(MachineRepresentation rep,
1111 28940 : BranchHint hint) {
1112 : return new (zone()) Operator1<SelectParameters>( // --
1113 : IrOpcode::kSelect, Operator::kPure, // opcode
1114 : "Select", // name
1115 : 3, 0, 0, 1, 0, 0, // counts
1116 28940 : SelectParameters(rep, hint)); // parameter
1117 : }
1118 :
1119 :
1120 7884899 : const Operator* CommonOperatorBuilder::Phi(MachineRepresentation rep,
1121 3180386 : int value_input_count) {
1122 : DCHECK(value_input_count > 0); // Disallow empty phis.
1123 : #define CACHED_PHI(kRep, kValueInputCount) \
1124 : if (MachineRepresentation::kRep == rep && \
1125 : kValueInputCount == value_input_count) { \
1126 : return &cache_.kPhi##kRep##kValueInputCount##Operator; \
1127 : }
1128 7884899 : CACHED_PHI_LIST(CACHED_PHI)
1129 : #undef CACHED_PHI
1130 : // Uncached.
1131 : return new (zone()) Operator1<MachineRepresentation>( // --
1132 : IrOpcode::kPhi, Operator::kPure, // opcode
1133 : "Phi", // name
1134 : value_input_count, 0, 1, 1, 0, 0, // counts
1135 3180385 : rep); // parameter
1136 : }
1137 :
1138 9277 : const Operator* CommonOperatorBuilder::TypeGuard(Type* type) {
1139 : return new (zone()) Operator1<Type*>( // --
1140 : IrOpcode::kTypeGuard, Operator::kPure, // opcode
1141 : "TypeGuard", // name
1142 : 1, 0, 1, 1, 0, 0, // counts
1143 9277 : type); // parameter
1144 : }
1145 :
1146 2343019 : const Operator* CommonOperatorBuilder::EffectPhi(int effect_input_count) {
1147 : DCHECK(effect_input_count > 0); // Disallow empty effect phis.
1148 2144285 : switch (effect_input_count) {
1149 : #define CACHED_EFFECT_PHI(input_count) \
1150 : case input_count: \
1151 : return &cache_.kEffectPhi##input_count##Operator;
1152 80123 : CACHED_EFFECT_PHI_LIST(CACHED_EFFECT_PHI)
1153 : #undef CACHED_EFFECT_PHI
1154 : default:
1155 : break;
1156 : }
1157 : // Uncached.
1158 : return new (zone()) Operator( // --
1159 : IrOpcode::kEffectPhi, Operator::kKontrol, // opcode
1160 : "EffectPhi", // name
1161 198734 : 0, effect_input_count, 1, 0, 1, 0); // counts
1162 : }
1163 :
1164 23041 : const Operator* CommonOperatorBuilder::InductionVariablePhi(int input_count) {
1165 : DCHECK(input_count >= 4); // There must be always the entry, backedge,
1166 : // increment and at least one bound.
1167 23041 : switch (input_count) {
1168 : #define CACHED_INDUCTION_VARIABLE_PHI(input_count) \
1169 : case input_count: \
1170 : return &cache_.kInductionVariablePhi##input_count##Operator;
1171 22843 : CACHED_INDUCTION_VARIABLE_PHI_LIST(CACHED_INDUCTION_VARIABLE_PHI)
1172 : #undef CACHED_INDUCTION_VARIABLE_PHI
1173 : default:
1174 : break;
1175 : }
1176 : // Uncached.
1177 : return new (zone()) Operator( // --
1178 : IrOpcode::kInductionVariablePhi, Operator::kPure, // opcode
1179 : "InductionVariablePhi", // name
1180 0 : input_count, 0, 1, 1, 0, 0); // counts
1181 : }
1182 :
1183 130259 : const Operator* CommonOperatorBuilder::BeginRegion(
1184 : RegionObservability region_observability) {
1185 130259 : switch (region_observability) {
1186 : case RegionObservability::kObservable:
1187 4529 : return &cache_.kBeginRegionObservableOperator;
1188 : case RegionObservability::kNotObservable:
1189 125730 : return &cache_.kBeginRegionNotObservableOperator;
1190 : }
1191 0 : UNREACHABLE();
1192 : return nullptr;
1193 : }
1194 :
1195 5865373 : const Operator* CommonOperatorBuilder::StateValues(int arguments,
1196 5332372 : SparseInputMask bitmask) {
1197 5865373 : if (bitmask.IsDense()) {
1198 533851 : switch (arguments) {
1199 : #define CACHED_STATE_VALUES(arguments) \
1200 : case arguments: \
1201 : return &cache_.kStateValues##arguments##Operator;
1202 118152 : CACHED_STATE_VALUES_LIST(CACHED_STATE_VALUES)
1203 : #undef CACHED_STATE_VALUES
1204 : default:
1205 : break;
1206 : }
1207 : }
1208 :
1209 : #if DEBUG
1210 : DCHECK(bitmask.IsDense() || bitmask.CountReal() == arguments);
1211 : #endif
1212 :
1213 : // Uncached.
1214 : return new (zone()) Operator1<SparseInputMask>( // --
1215 : IrOpcode::kStateValues, Operator::kPure, // opcode
1216 : "StateValues", // name
1217 : arguments, 0, 0, 1, 0, 0, // counts
1218 5332373 : bitmask); // parameter
1219 : }
1220 :
1221 4524849 : const Operator* CommonOperatorBuilder::TypedStateValues(
1222 4524849 : const ZoneVector<MachineType>* types, SparseInputMask bitmask) {
1223 : #if DEBUG
1224 : DCHECK(bitmask.IsDense() ||
1225 : bitmask.CountReal() == static_cast<int>(types->size()));
1226 : #endif
1227 :
1228 : return new (zone()) Operator1<TypedStateValueInfo>( // --
1229 : IrOpcode::kTypedStateValues, Operator::kPure, // opcode
1230 : "TypedStateValues", // name
1231 4524849 : static_cast<int>(types->size()), 0, 0, 1, 0, 0, // counts
1232 9049693 : TypedStateValueInfo(types, bitmask)); // parameters
1233 : }
1234 :
1235 1224 : const Operator* CommonOperatorBuilder::ArgumentsElementsState(bool is_rest) {
1236 : return new (zone()) Operator1<bool>( // --
1237 : IrOpcode::kArgumentsElementsState, Operator::kPure, // opcode
1238 : "ArgumentsElementsState", // name
1239 1224 : 0, 0, 0, 1, 0, 0, is_rest); // counts
1240 : }
1241 :
1242 608 : const Operator* CommonOperatorBuilder::ArgumentsLengthState(bool is_rest) {
1243 : return new (zone()) Operator1<bool>( // --
1244 : IrOpcode::kArgumentsLengthState, Operator::kPure, // opcode
1245 : "ArgumentsLengthState", // name
1246 608 : 0, 0, 0, 1, 0, 0, is_rest); // counts
1247 : }
1248 :
1249 5236 : bool IsRestOf(Operator const* op) {
1250 : DCHECK(op->opcode() == IrOpcode::kArgumentsElementsState ||
1251 : op->opcode() == IrOpcode::kArgumentsLengthState);
1252 5236 : return OpParameter<bool>(op);
1253 : }
1254 :
1255 8835 : const Operator* CommonOperatorBuilder::ObjectState(int pointer_slots) {
1256 : return new (zone()) Operator1<int>( // --
1257 : IrOpcode::kObjectState, Operator::kPure, // opcode
1258 : "ObjectState", // name
1259 : pointer_slots, 0, 0, 1, 0, 0, // counts
1260 17670 : pointer_slots); // parameter
1261 : }
1262 :
1263 8834 : const Operator* CommonOperatorBuilder::TypedObjectState(
1264 8834 : const ZoneVector<MachineType>* types) {
1265 : return new (zone()) Operator1<const ZoneVector<MachineType>*>( // --
1266 : IrOpcode::kTypedObjectState, Operator::kPure, // opcode
1267 : "TypedObjectState", // name
1268 8834 : static_cast<int>(types->size()), 0, 0, 1, 0, 0, // counts
1269 17668 : types); // parameter
1270 : }
1271 :
1272 5992786 : const Operator* CommonOperatorBuilder::FrameState(
1273 : BailoutId bailout_id, OutputFrameStateCombine state_combine,
1274 5992786 : const FrameStateFunctionInfo* function_info) {
1275 : FrameStateInfo state_info(bailout_id, state_combine, function_info);
1276 : return new (zone()) Operator1<FrameStateInfo>( // --
1277 : IrOpcode::kFrameState, Operator::kPure, // opcode
1278 : "FrameState", // name
1279 : 5, 0, 0, 1, 0, 0, // counts
1280 5992788 : state_info); // parameter
1281 : }
1282 :
1283 :
1284 3360772 : const Operator* CommonOperatorBuilder::Call(const CallDescriptor* descriptor) {
1285 0 : class CallOperator final : public Operator1<const CallDescriptor*> {
1286 : public:
1287 6721574 : explicit CallOperator(const CallDescriptor* descriptor)
1288 : : Operator1<const CallDescriptor*>(
1289 : IrOpcode::kCall, descriptor->properties(), "Call",
1290 : descriptor->InputCount() + descriptor->FrameStateCount(),
1291 : Operator::ZeroIfPure(descriptor->properties()),
1292 : Operator::ZeroIfEliminatable(descriptor->properties()),
1293 : descriptor->ReturnCount(),
1294 : Operator::ZeroIfPure(descriptor->properties()),
1295 6721595 : Operator::ZeroIfNoThrow(descriptor->properties()), descriptor) {}
1296 :
1297 0 : void PrintParameter(std::ostream& os, PrintVerbosity verbose) const {
1298 0 : os << "[" << *parameter() << "]";
1299 0 : }
1300 : };
1301 3360791 : return new (zone()) CallOperator(descriptor);
1302 : }
1303 :
1304 :
1305 149228 : const Operator* CommonOperatorBuilder::TailCall(
1306 149228 : const CallDescriptor* descriptor) {
1307 0 : class TailCallOperator final : public Operator1<const CallDescriptor*> {
1308 : public:
1309 149227 : explicit TailCallOperator(const CallDescriptor* descriptor)
1310 : : Operator1<const CallDescriptor*>(
1311 : IrOpcode::kTailCall,
1312 : descriptor->properties() | Operator::kNoThrow, "TailCall",
1313 : descriptor->InputCount() + descriptor->FrameStateCount(), 1, 1, 0,
1314 298454 : 0, 1, descriptor) {}
1315 :
1316 0 : void PrintParameter(std::ostream& os, PrintVerbosity verbose) const {
1317 0 : os << "[" << *parameter() << "]";
1318 0 : }
1319 : };
1320 149227 : return new (zone()) TailCallOperator(descriptor);
1321 : }
1322 :
1323 :
1324 466199 : const Operator* CommonOperatorBuilder::Projection(size_t index) {
1325 464562 : switch (index) {
1326 : #define CACHED_PROJECTION(index) \
1327 : case index: \
1328 : return &cache_.kProjection##index##Operator;
1329 231461 : CACHED_PROJECTION_LIST(CACHED_PROJECTION)
1330 : #undef CACHED_PROJECTION
1331 : default:
1332 : break;
1333 : }
1334 : // Uncached.
1335 : return new (zone()) Operator1<size_t>( // --
1336 : IrOpcode::kProjection, // opcode
1337 : Operator::kPure, // flags
1338 : "Projection", // name
1339 : 1, 0, 1, 1, 0, 0, // counts
1340 : index); // parameter
1341 : }
1342 :
1343 :
1344 893397 : const Operator* CommonOperatorBuilder::ResizeMergeOrPhi(const Operator* op,
1345 : int size) {
1346 893397 : if (op->opcode() == IrOpcode::kPhi) {
1347 474419 : return Phi(PhiRepresentationOf(op), size);
1348 418978 : } else if (op->opcode() == IrOpcode::kEffectPhi) {
1349 204949 : return EffectPhi(size);
1350 214029 : } else if (op->opcode() == IrOpcode::kMerge) {
1351 197576 : return Merge(size);
1352 16453 : } else if (op->opcode() == IrOpcode::kLoop) {
1353 16453 : return Loop(size);
1354 : } else {
1355 0 : UNREACHABLE();
1356 : return nullptr;
1357 : }
1358 : }
1359 :
1360 : const FrameStateFunctionInfo*
1361 447500 : CommonOperatorBuilder::CreateFrameStateFunctionInfo(
1362 : FrameStateType type, int parameter_count, int local_count,
1363 447500 : Handle<SharedFunctionInfo> shared_info) {
1364 : return new (zone()->New(sizeof(FrameStateFunctionInfo)))
1365 1342500 : FrameStateFunctionInfo(type, parameter_count, local_count, shared_info);
1366 : }
1367 :
1368 : } // namespace compiler
1369 : } // namespace internal
1370 : } // namespace v8
|