1// Copyright 2017 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#ifndef V8_COMPILER_ALLOCATION_BUILDER_H_
6#define V8_COMPILER_ALLOCATION_BUILDER_H_
7
8#include "src/compiler/js-graph.h"
9#include "src/compiler/node.h"
10#include "src/compiler/simplified-operator.h"
11
12namespace v8 {
13namespace internal {
14namespace compiler {
15
16// A helper class to construct inline allocations on the simplified operator
17// level. This keeps track of the effect chain for initial stores on a newly
18// allocated object and also provides helpers for commonly allocated objects.
19class AllocationBuilder final {
20 public:
21  AllocationBuilder(JSGraph* jsgraph, Node* effect, Node* control)
22      : jsgraph_(jsgraph),
23        allocation_(nullptr),
24        effect_(effect),
25        control_(control) {}
26
27  // Primitive allocation of static size.
28  inline void Allocate(int size,
29                       AllocationType allocation = AllocationType::kYoung,
30                       Type type = Type::Any());
31
32  // Primitive store into a field.
33  void Store(const FieldAccess& access, Node* value) {
34    effect_ = graph()->NewNode(simplified()->StoreField(access), allocation_,
35                               value, effect_, control_);
36  }
37
38  // Primitive store into an element.
39  void Store(ElementAccess const& access, Node* index, Node* value) {
40    effect_ = graph()->NewNode(simplified()->StoreElement(access), allocation_,
41                               index, value, effect_, control_);
42  }
43
44  // Compound allocation of a context.
45  inline void AllocateContext(int variadic_part_length, MapRef map);
46
47  // Compound allocation of a FixedArray.
48  inline bool CanAllocateArray(
49      int length, MapRef map,
50      AllocationType allocation = AllocationType::kYoung);
51  inline void AllocateArray(int length, MapRef map,
52                            AllocationType allocation = AllocationType::kYoung);
53
54  // Compound allocation of a SloppyArgumentsElements
55  inline bool CanAllocateSloppyArgumentElements(
56      int length, MapRef map,
57      AllocationType allocation = AllocationType::kYoung);
58  inline void AllocateSloppyArgumentElements(
59      int length, MapRef map,
60      AllocationType allocation = AllocationType::kYoung);
61
62  // Compound store of a constant into a field.
63  void Store(const FieldAccess& access, const ObjectRef& value) {
64    Store(access, jsgraph()->Constant(value));
65  }
66
67  void FinishAndChange(Node* node) {
68    NodeProperties::SetType(allocation_, NodeProperties::GetType(node));
69    node->ReplaceInput(0, allocation_);
70    node->ReplaceInput(1, effect_);
71    node->TrimInputCount(2);
72    NodeProperties::ChangeOp(node, common()->FinishRegion());
73  }
74
75  Node* Finish() {
76    return graph()->NewNode(common()->FinishRegion(), allocation_, effect_);
77  }
78
79 protected:
80  JSGraph* jsgraph() { return jsgraph_; }
81  Isolate* isolate() const { return jsgraph_->isolate(); }
82  Graph* graph() { return jsgraph_->graph(); }
83  CommonOperatorBuilder* common() { return jsgraph_->common(); }
84  SimplifiedOperatorBuilder* simplified() { return jsgraph_->simplified(); }
85
86 private:
87  JSGraph* const jsgraph_;
88  Node* allocation_;
89  Node* effect_;
90  Node* control_;
91};
92
93}  // namespace compiler
94}  // namespace internal
95}  // namespace v8
96
97#endif  // V8_COMPILER_ALLOCATION_BUILDER_H_
98