V8 API Reference, 7.2.502.16 (for Deno 0.2.4)
maybe-object.h
1 // Copyright 2018 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_OBJECTS_MAYBE_OBJECT_H_
6 #define V8_OBJECTS_MAYBE_OBJECT_H_
7 
8 #include "include/v8-internal.h"
9 #include "include/v8.h"
10 #include "src/globals.h"
11 #include "src/objects.h"
12 #include "src/objects/slots.h"
13 #include "src/objects/smi.h"
14 
15 namespace v8 {
16 namespace internal {
17 
18 class HeapObject;
19 class Isolate;
20 class StringStream;
21 
22 // A MaybeObject is either a SMI, a strong reference to a HeapObject, a weak
23 // reference to a HeapObject, or a cleared weak reference. It's used for
24 // implementing in-place weak references (see design doc: goo.gl/j6SdcK )
25 class MaybeObject {
26  public:
27  MaybeObject() : ptr_(kNullAddress) {}
28  explicit MaybeObject(Address ptr) : ptr_(ptr) {}
29 
30  bool operator==(const MaybeObject& other) const { return ptr_ == other.ptr_; }
31  bool operator!=(const MaybeObject& other) const { return ptr_ != other.ptr_; }
32 
33  Address ptr() const { return ptr_; }
34 
35  // Enable incremental transition of client code.
36  MaybeObject* operator->() { return this; }
37  const MaybeObject* operator->() const { return this; }
38 
39  bool IsSmi() const { return HAS_SMI_TAG(ptr_); }
40  inline bool ToSmi(Smi* value);
41  inline Smi ToSmi() const;
42 
43  bool IsCleared() const {
44  return static_cast<uint32_t>(ptr_) == kClearedWeakHeapObjectLower32;
45  }
46 
47  inline bool IsStrongOrWeak() const;
48  inline bool IsStrong() const;
49 
50  // If this MaybeObject is a strong pointer to a HeapObject, returns true and
51  // sets *result. Otherwise returns false.
52  inline bool GetHeapObjectIfStrong(HeapObject** result) const;
53 
54  // DCHECKs that this MaybeObject is a strong pointer to a HeapObject and
55  // returns the HeapObject.
56  inline HeapObject* GetHeapObjectAssumeStrong() const;
57 
58  inline bool IsWeak() const;
59  inline bool IsWeakOrCleared() const;
60 
61  // If this MaybeObject is a weak pointer to a HeapObject, returns true and
62  // sets *result. Otherwise returns false.
63  inline bool GetHeapObjectIfWeak(HeapObject** result) const;
64 
65  // DCHECKs that this MaybeObject is a weak pointer to a HeapObject and
66  // returns the HeapObject.
67  inline HeapObject* GetHeapObjectAssumeWeak() const;
68 
69  // If this MaybeObject is a strong or weak pointer to a HeapObject, returns
70  // true and sets *result. Otherwise returns false.
71  inline bool GetHeapObject(HeapObject** result) const;
72  inline bool GetHeapObject(HeapObject** result,
73  HeapObjectReferenceType* reference_type) const;
74 
75  // DCHECKs that this MaybeObject is a strong or a weak pointer to a HeapObject
76  // and returns the HeapObject.
77  inline HeapObject* GetHeapObject() const;
78 
79  // DCHECKs that this MaybeObject is a strong or a weak pointer to a HeapObject
80  // or a SMI and returns the HeapObject or SMI.
81  inline Object* GetHeapObjectOrSmi() const;
82 
83  inline bool IsObject() const;
84  template <typename T, typename = typename std::enable_if<
85  std::is_base_of<Object, T>::value>::type>
86  T* cast() const {
87  DCHECK(!HasWeakHeapObjectTag(ptr_));
88  return T::cast(reinterpret_cast<Object*>(ptr_));
89  }
90  // Replacement for the above, temporarily separate for incremental transition.
91  // TODO(3770): Get rid of the duplication.
92  template <typename T, typename = typename std::enable_if<
93  std::is_base_of<ObjectPtr, T>::value>::type>
94  T cast() const {
95  DCHECK(!HasWeakHeapObjectTag(ptr_));
96  return T::cast(ObjectPtr(ptr_));
97  }
98 
99  static MaybeObject FromSmi(Smi smi) {
100  DCHECK(HAS_SMI_TAG(smi->ptr()));
101  return MaybeObject(smi->ptr());
102  }
103 
104  static MaybeObject FromObject(Object* object) {
105  DCHECK(!HasWeakHeapObjectTag(object));
106  return MaybeObject(object->ptr());
107  }
108 
109  static MaybeObject FromObject(ObjectPtr object) {
110  DCHECK(!HasWeakHeapObjectTag(object.ptr()));
111  return MaybeObject(object.ptr());
112  }
113 
114  static inline MaybeObject MakeWeak(MaybeObject object);
115 
116 #ifdef VERIFY_HEAP
117  static void VerifyMaybeObjectPointer(Isolate* isolate, MaybeObject p);
118 #endif
119 
120  // Prints this object without details.
121  void ShortPrint(FILE* out = stdout);
122 
123  // Prints this object without details to a message accumulator.
124  void ShortPrint(StringStream* accumulator);
125 
126  void ShortPrint(std::ostream& os);
127 
128 #ifdef OBJECT_PRINT
129  void Print();
130  void Print(std::ostream& os);
131 #else
132  void Print() { ShortPrint(); }
133  void Print(std::ostream& os) { ShortPrint(os); }
134 #endif
135 
136  private:
137  Address ptr_;
138 };
139 
140 // A HeapObjectReference is either a strong reference to a HeapObject, a weak
141 // reference to a HeapObject, or a cleared weak reference.
143  public:
144  explicit HeapObjectReference(Address address) : MaybeObject(address) {}
145  explicit HeapObjectReference(Object* object) : MaybeObject(object->ptr()) {}
146 
147  static HeapObjectReference Strong(Object* object) {
148  DCHECK(!object->IsSmi());
149  DCHECK(!HasWeakHeapObjectTag(object));
150  return HeapObjectReference(object);
151  }
152 
153  static HeapObjectReference Weak(Object* object) {
154  DCHECK(!object->IsSmi());
155  DCHECK(!HasWeakHeapObjectTag(object));
156  return HeapObjectReference(object->ptr() | kWeakHeapObjectMask);
157  }
158 
159  V8_INLINE static HeapObjectReference ClearedValue(Isolate* isolate);
160 
161  V8_INLINE static void Update(HeapObjectSlot slot, HeapObject* value);
162 };
163 
164 } // namespace internal
165 } // namespace v8
166 
167 #endif // V8_OBJECTS_MAYBE_OBJECT_H_
Definition: libplatform.h:13