• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2019 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_TAGGED_FIELD_INL_H_
6 #define V8_OBJECTS_TAGGED_FIELD_INL_H_
7 
8 #include "src/objects/tagged-field.h"
9 
10 #include "src/common/ptr-compr-inl.h"
11 
12 namespace v8 {
13 namespace internal {
14 
15 // static
16 template <typename T, int kFieldOffset>
address(HeapObject host,int offset)17 Address TaggedField<T, kFieldOffset>::address(HeapObject host, int offset) {
18   return host.address() + kFieldOffset + offset;
19 }
20 
21 // static
22 template <typename T, int kFieldOffset>
location(HeapObject host,int offset)23 Tagged_t* TaggedField<T, kFieldOffset>::location(HeapObject host, int offset) {
24   return reinterpret_cast<Tagged_t*>(address(host, offset));
25 }
26 
27 // static
28 template <typename T, int kFieldOffset>
29 template <typename TOnHeapAddress>
tagged_to_full(TOnHeapAddress on_heap_addr,Tagged_t tagged_value)30 Address TaggedField<T, kFieldOffset>::tagged_to_full(
31     TOnHeapAddress on_heap_addr, Tagged_t tagged_value) {
32 #ifdef V8_COMPRESS_POINTERS
33   if (kIsSmi) {
34     return DecompressTaggedSigned(tagged_value);
35   } else if (kIsHeapObject) {
36     return DecompressTaggedPointer(on_heap_addr, tagged_value);
37   } else {
38     return DecompressTaggedAny(on_heap_addr, tagged_value);
39   }
40 #else
41   return tagged_value;
42 #endif
43 }
44 
45 // static
46 template <typename T, int kFieldOffset>
full_to_tagged(Address value)47 Tagged_t TaggedField<T, kFieldOffset>::full_to_tagged(Address value) {
48 #ifdef V8_COMPRESS_POINTERS
49   return CompressTagged(value);
50 #else
51   return value;
52 #endif
53 }
54 
55 // static
56 template <typename T, int kFieldOffset>
load(HeapObject host,int offset)57 T TaggedField<T, kFieldOffset>::load(HeapObject host, int offset) {
58   Tagged_t value = *location(host, offset);
59   return T(tagged_to_full(host.ptr(), value));
60 }
61 
62 // static
63 template <typename T, int kFieldOffset>
load(IsolateRoot isolate,HeapObject host,int offset)64 T TaggedField<T, kFieldOffset>::load(IsolateRoot isolate, HeapObject host,
65                                      int offset) {
66   Tagged_t value = *location(host, offset);
67   return T(tagged_to_full(isolate, value));
68 }
69 
70 // static
71 template <typename T, int kFieldOffset>
store(HeapObject host,T value)72 void TaggedField<T, kFieldOffset>::store(HeapObject host, T value) {
73 #ifdef V8_ATOMIC_OBJECT_FIELD_WRITES
74   Relaxed_Store(host, value);
75 #else
76   *location(host) = full_to_tagged(value.ptr());
77 #endif
78 }
79 
80 // static
81 template <typename T, int kFieldOffset>
store(HeapObject host,int offset,T value)82 void TaggedField<T, kFieldOffset>::store(HeapObject host, int offset, T value) {
83 #ifdef V8_ATOMIC_OBJECT_FIELD_WRITES
84   Relaxed_Store(host, offset, value);
85 #else
86   *location(host, offset) = full_to_tagged(value.ptr());
87 #endif
88 }
89 
90 // static
91 template <typename T, int kFieldOffset>
Relaxed_Load(HeapObject host,int offset)92 T TaggedField<T, kFieldOffset>::Relaxed_Load(HeapObject host, int offset) {
93   AtomicTagged_t value = AsAtomicTagged::Relaxed_Load(location(host, offset));
94   return T(tagged_to_full(host.ptr(), value));
95 }
96 
97 // static
98 template <typename T, int kFieldOffset>
Relaxed_Load(IsolateRoot isolate,HeapObject host,int offset)99 T TaggedField<T, kFieldOffset>::Relaxed_Load(IsolateRoot isolate,
100                                              HeapObject host, int offset) {
101   AtomicTagged_t value = AsAtomicTagged::Relaxed_Load(location(host, offset));
102   return T(tagged_to_full(isolate, value));
103 }
104 
105 // static
106 template <typename T, int kFieldOffset>
Relaxed_Store(HeapObject host,T value)107 void TaggedField<T, kFieldOffset>::Relaxed_Store(HeapObject host, T value) {
108   AsAtomicTagged::Relaxed_Store(location(host), full_to_tagged(value.ptr()));
109 }
110 
111 // static
112 template <typename T, int kFieldOffset>
Relaxed_Store(HeapObject host,int offset,T value)113 void TaggedField<T, kFieldOffset>::Relaxed_Store(HeapObject host, int offset,
114                                                  T value) {
115   AsAtomicTagged::Relaxed_Store(location(host, offset),
116                                 full_to_tagged(value.ptr()));
117 }
118 
119 // static
120 template <typename T, int kFieldOffset>
Acquire_Load(HeapObject host,int offset)121 T TaggedField<T, kFieldOffset>::Acquire_Load(HeapObject host, int offset) {
122   AtomicTagged_t value = AsAtomicTagged::Acquire_Load(location(host, offset));
123   return T(tagged_to_full(host.ptr(), value));
124 }
125 
126 // static
127 template <typename T, int kFieldOffset>
Acquire_Load(IsolateRoot isolate,HeapObject host,int offset)128 T TaggedField<T, kFieldOffset>::Acquire_Load(IsolateRoot isolate,
129                                              HeapObject host, int offset) {
130   AtomicTagged_t value = AsAtomicTagged::Acquire_Load(location(host, offset));
131   return T(tagged_to_full(isolate, value));
132 }
133 
134 // static
135 template <typename T, int kFieldOffset>
Release_Store(HeapObject host,T value)136 void TaggedField<T, kFieldOffset>::Release_Store(HeapObject host, T value) {
137   AsAtomicTagged::Release_Store(location(host), full_to_tagged(value.ptr()));
138 }
139 
140 // static
141 template <typename T, int kFieldOffset>
Release_Store(HeapObject host,int offset,T value)142 void TaggedField<T, kFieldOffset>::Release_Store(HeapObject host, int offset,
143                                                  T value) {
144   AsAtomicTagged::Release_Store(location(host, offset),
145                                 full_to_tagged(value.ptr()));
146 }
147 
148 // static
149 template <typename T, int kFieldOffset>
Release_CompareAndSwap(HeapObject host,T old,T value)150 Tagged_t TaggedField<T, kFieldOffset>::Release_CompareAndSwap(HeapObject host,
151                                                               T old, T value) {
152   Tagged_t old_value = full_to_tagged(old.ptr());
153   Tagged_t new_value = full_to_tagged(value.ptr());
154   Tagged_t result = AsAtomicTagged::Release_CompareAndSwap(
155       location(host), old_value, new_value);
156   return result;
157 }
158 
159 }  // namespace internal
160 }  // namespace v8
161 
162 #endif  // V8_OBJECTS_TAGGED_FIELD_INL_H_
163