• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1  // Copyright 2016 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  // Note 1: Any file that includes this one should include object-macros-undef.h
6  // at the bottom.
7  
8  // Note 2: This file is deliberately missing the include guards (the undeffing
9  // approach wouldn't work otherwise).
10  //
11  // PRESUBMIT_INTENTIONALLY_MISSING_INCLUDE_GUARD
12  
13  // The accessors with RELAXED_, ACQUIRE_, and RELEASE_ prefixes should be used
14  // for fields that can be written to and read from multiple threads at the same
15  // time. See comments in src/base/atomicops.h for the memory ordering sematics.
16  
17  #include "src/base/memory.h"
18  
19  // Since this changes visibility, it should always be last in a class
20  // definition.
21  #define OBJECT_CONSTRUCTORS(Type, ...)             \
22   public:                                           \
23    constexpr Type() : __VA_ARGS__() {}              \
24                                                     \
25   protected:                                        \
26    template <typename TFieldType, int kFieldOffset> \
27    friend class TaggedField;                        \
28                                                     \
29    explicit inline Type(Address ptr)
30  
31  #define OBJECT_CONSTRUCTORS_IMPL(Type, Super) \
32    inline Type::Type(Address ptr) : Super(ptr) { SLOW_DCHECK(Is##Type()); }
33  // In these cases, we don't have our own instance type to check, so check the
34  // supertype instead. This happens for types denoting a NativeContext-dependent
35  // set of maps.
36  #define OBJECT_CONSTRUCTORS_IMPL_CHECK_SUPER(Type, Super) \
37    inline Type::Type(Address ptr) : Super(ptr) { SLOW_DCHECK(Is##Super()); }
38  
39  #define NEVER_READ_ONLY_SPACE   \
40    inline Heap* GetHeap() const; \
41    inline Isolate* GetIsolate() const;
42  
43  // TODO(leszeks): Add checks in the factory that we never allocate these
44  // objects in RO space.
45  #define NEVER_READ_ONLY_SPACE_IMPL(Type)                                   \
46    Heap* Type::GetHeap() const { return GetHeapFromWritableObject(*this); } \
47    Isolate* Type::GetIsolate() const {                                      \
48      return GetIsolateFromWritableObject(*this);                            \
49    }
50  
51  #define DECL_PRIMITIVE_ACCESSORS(name, type) \
52    inline type name() const;                  \
53    inline void set_##name(type value);
54  
55  #define DECL_SYNCHRONIZED_PRIMITIVE_ACCESSORS(name, type) \
56    inline type synchronized_##name() const;                \
57    inline void synchronized_set_##name(type value);
58  
59  #define DECL_BOOLEAN_ACCESSORS(name) DECL_PRIMITIVE_ACCESSORS(name, bool)
60  
61  #define DECL_INT_ACCESSORS(name) DECL_PRIMITIVE_ACCESSORS(name, int)
62  
63  #define DECL_SYNCHRONIZED_INT_ACCESSORS(name) \
64    DECL_SYNCHRONIZED_PRIMITIVE_ACCESSORS(name, int)
65  
66  #define DECL_INT32_ACCESSORS(name) DECL_PRIMITIVE_ACCESSORS(name, int32_t)
67  
68  #define DECL_UINT16_ACCESSORS(name) \
69    inline uint16_t name() const;     \
70    inline void set_##name(int value);
71  
72  #define DECL_INT16_ACCESSORS(name) \
73    inline int16_t name() const;     \
74    inline void set_##name(int16_t value);
75  
76  #define DECL_UINT8_ACCESSORS(name) \
77    inline uint8_t name() const;     \
78    inline void set_##name(int value);
79  
80  // TODO(ishell): eventually isolate-less getters should not be used anymore.
81  // For full pointer-mode the C++ compiler should optimize away unused isolate
82  // parameter.
83  #define DECL_GETTER(name, type) \
84    inline type name() const;     \
85    inline type name(IsolateRoot isolate) const;
86  
87  #define DEF_GETTER(holder, name, type)                  \
88    type holder::name() const {                           \
89      IsolateRoot isolate = GetIsolateForPtrCompr(*this); \
90      return holder::name(isolate);                       \
91    }                                                     \
92    type holder::name(IsolateRoot isolate) const
93  
94  #define DECL_ACCESSORS(name, type)   \
95    DECL_GETTER(name, type)            \
96    inline void set_##name(type value, \
97                           WriteBarrierMode mode = UPDATE_WRITE_BARRIER);
98  
99  #define DECL_ACCESSORS_LOAD_TAG(name, type, tag_type) \
100    inline type name(tag_type tag) const;               \
101    inline type name(IsolateRoot isolate, tag_type) const;
102  
103  #define DECL_ACCESSORS_STORE_TAG(name, type, tag_type) \
104    inline void set_##name(type value, tag_type,         \
105                           WriteBarrierMode mode = UPDATE_WRITE_BARRIER);
106  
107  #define DECL_RELAXED_GETTER(name, type) \
108    DECL_ACCESSORS_LOAD_TAG(name, type, RelaxedLoadTag)
109  
110  #define DECL_RELAXED_SETTER(name, type) \
111    DECL_ACCESSORS_STORE_TAG(name, type, RelaxedStoreTag)
112  
113  #define DECL_RELAXED_ACCESSORS(name, type) \
114    DECL_RELAXED_GETTER(name, type)          \
115    DECL_RELAXED_SETTER(name, type)
116  
117  #define DECL_ACQUIRE_GETTER(name, type) \
118    DECL_ACCESSORS_LOAD_TAG(name, type, AcquireLoadTag)
119  
120  #define DECL_RELEASE_SETTER(name, type) \
121    DECL_ACCESSORS_STORE_TAG(name, type, ReleaseStoreTag)
122  
123  #define DECL_RELEASE_ACQUIRE_ACCESSORS(name, type) \
124    DECL_ACQUIRE_GETTER(name, type)                  \
125    DECL_RELEASE_SETTER(name, type)
126  
127  #define DECL_CAST(Type)                                 \
128    V8_INLINE static Type cast(Object object);            \
129    V8_INLINE static Type unchecked_cast(Object object) { \
130      return bit_cast<Type>(object);                      \
131    }
132  
133  #define CAST_ACCESSOR(Type) \
134    Type Type::cast(Object object) { return Type(object.ptr()); }
135  
136  #define INT_ACCESSORS(holder, name, offset)                   \
137    int holder::name() const { return ReadField<int>(offset); } \
138    void holder::set_##name(int value) { WriteField<int>(offset, value); }
139  
140  #define INT32_ACCESSORS(holder, name, offset)                         \
141    int32_t holder::name() const { return ReadField<int32_t>(offset); } \
142    void holder::set_##name(int32_t value) { WriteField<int32_t>(offset, value); }
143  
144  #define RELAXED_INT32_ACCESSORS(holder, name, offset) \
145    int32_t holder::name() const {                      \
146      return RELAXED_READ_INT32_FIELD(*this, offset);   \
147    }                                                   \
148    void holder::set_##name(int32_t value) {            \
149      RELAXED_WRITE_INT32_FIELD(*this, offset, value);  \
150    }
151  
152  #define UINT16_ACCESSORS(holder, name, offset)                          \
153    uint16_t holder::name() const { return ReadField<uint16_t>(offset); } \
154    void holder::set_##name(int value) {                                  \
155      DCHECK_GE(value, 0);                                                \
156      DCHECK_LE(value, static_cast<uint16_t>(-1));                        \
157      WriteField<uint16_t>(offset, value);                                \
158    }
159  
160  #define UINT8_ACCESSORS(holder, name, offset)                         \
161    uint8_t holder::name() const { return ReadField<uint8_t>(offset); } \
162    void holder::set_##name(int value) {                                \
163      DCHECK_GE(value, 0);                                              \
164      DCHECK_LE(value, static_cast<uint8_t>(-1));                       \
165      WriteField<uint8_t>(offset, value);                               \
166    }
167  
168  #define ACCESSORS_CHECKED2(holder, name, type, offset, get_condition, \
169                             set_condition)                             \
170    DEF_GETTER(holder, name, type) {                                    \
171      type value = TaggedField<type, offset>::load(isolate, *this);     \
172      DCHECK(get_condition);                                            \
173      return value;                                                     \
174    }                                                                   \
175    void holder::set_##name(type value, WriteBarrierMode mode) {        \
176      DCHECK(set_condition);                                            \
177      TaggedField<type, offset>::store(*this, value);                   \
178      CONDITIONAL_WRITE_BARRIER(*this, offset, value, mode);            \
179    }
180  
181  #define ACCESSORS_CHECKED(holder, name, type, offset, condition) \
182    ACCESSORS_CHECKED2(holder, name, type, offset, condition, condition)
183  
184  #define ACCESSORS(holder, name, type, offset) \
185    ACCESSORS_CHECKED(holder, name, type, offset, true)
186  
187  #define RELAXED_ACCESSORS_CHECKED2(holder, name, type, offset, get_condition, \
188                                     set_condition)                             \
189    type holder::name(RelaxedLoadTag tag) const {                               \
190      IsolateRoot isolate = GetIsolateForPtrCompr(*this);                       \
191      return holder::name(isolate, tag);                                        \
192    }                                                                           \
193    type holder::name(IsolateRoot isolate, RelaxedLoadTag) const {              \
194      type value = TaggedField<type, offset>::load(isolate, *this);             \
195      DCHECK(get_condition);                                                    \
196      return value;                                                             \
197    }                                                                           \
198    void holder::set_##name(type value, RelaxedStoreTag,                        \
199                            WriteBarrierMode mode) {                            \
200      DCHECK(set_condition);                                                    \
201      TaggedField<type, offset>::store(*this, value);                           \
202      CONDITIONAL_WRITE_BARRIER(*this, offset, value, mode);                    \
203    }
204  
205  #define RELAXED_ACCESSORS_CHECKED(holder, name, type, offset, condition) \
206    RELAXED_ACCESSORS_CHECKED2(holder, name, type, offset, condition, condition)
207  
208  #define RELAXED_ACCESSORS(holder, name, type, offset) \
209    RELAXED_ACCESSORS_CHECKED(holder, name, type, offset, true)
210  
211  #define RELEASE_ACQUIRE_ACCESSORS_CHECKED2(holder, name, type, offset,    \
212                                             get_condition, set_condition)  \
213    type holder::name(AcquireLoadTag tag) const {                           \
214      IsolateRoot isolate = GetIsolateForPtrCompr(*this);                   \
215      return holder::name(isolate, tag);                                    \
216    }                                                                       \
217    type holder::name(IsolateRoot isolate, AcquireLoadTag) const {          \
218      type value = TaggedField<type, offset>::Acquire_Load(isolate, *this); \
219      DCHECK(get_condition);                                                \
220      return value;                                                         \
221    }                                                                       \
222    void holder::set_##name(type value, ReleaseStoreTag,                    \
223                            WriteBarrierMode mode) {                        \
224      DCHECK(set_condition);                                                \
225      TaggedField<type, offset>::Release_Store(*this, value);               \
226      CONDITIONAL_WRITE_BARRIER(*this, offset, value, mode);                \
227    }
228  
229  #define RELEASE_ACQUIRE_ACCESSORS_CHECKED(holder, name, type, offset,       \
230                                            condition)                        \
231    RELEASE_ACQUIRE_ACCESSORS_CHECKED2(holder, name, type, offset, condition, \
232                                       condition)
233  
234  #define RELEASE_ACQUIRE_ACCESSORS(holder, name, type, offset) \
235    RELEASE_ACQUIRE_ACCESSORS_CHECKED(holder, name, type, offset, true)
236  
237  #define WEAK_ACCESSORS_CHECKED2(holder, name, offset, get_condition,  \
238                                  set_condition)                        \
239    DEF_GETTER(holder, name, MaybeObject) {                             \
240      MaybeObject value =                                               \
241          TaggedField<MaybeObject, offset>::load(isolate, *this);       \
242      DCHECK(get_condition);                                            \
243      return value;                                                     \
244    }                                                                   \
245    void holder::set_##name(MaybeObject value, WriteBarrierMode mode) { \
246      DCHECK(set_condition);                                            \
247      TaggedField<MaybeObject, offset>::store(*this, value);            \
248      CONDITIONAL_WEAK_WRITE_BARRIER(*this, offset, value, mode);       \
249    }
250  
251  #define WEAK_ACCESSORS_CHECKED(holder, name, offset, condition) \
252    WEAK_ACCESSORS_CHECKED2(holder, name, offset, condition, condition)
253  
254  #define WEAK_ACCESSORS(holder, name, offset) \
255    WEAK_ACCESSORS_CHECKED(holder, name, offset, true)
256  
257  #define SYNCHRONIZED_WEAK_ACCESSORS_CHECKED2(holder, name, offset,         \
258                                               get_condition, set_condition) \
259    DEF_GETTER(holder, name, MaybeObject) {                                  \
260      MaybeObject value =                                                    \
261          TaggedField<MaybeObject, offset>::Acquire_Load(isolate, *this);    \
262      DCHECK(get_condition);                                                 \
263      return value;                                                          \
264    }                                                                        \
265    void holder::set_##name(MaybeObject value, WriteBarrierMode mode) {      \
266      DCHECK(set_condition);                                                 \
267      TaggedField<MaybeObject, offset>::Release_Store(*this, value);         \
268      CONDITIONAL_WEAK_WRITE_BARRIER(*this, offset, value, mode);            \
269    }
270  
271  #define SYNCHRONIZED_WEAK_ACCESSORS_CHECKED(holder, name, offset, condition) \
272    SYNCHRONIZED_WEAK_ACCESSORS_CHECKED2(holder, name, offset, condition,      \
273                                         condition)
274  
275  #define SYNCHRONIZED_WEAK_ACCESSORS(holder, name, offset) \
276    SYNCHRONIZED_WEAK_ACCESSORS_CHECKED(holder, name, offset, true)
277  
278  // Getter that returns a Smi as an int and writes an int as a Smi.
279  #define SMI_ACCESSORS_CHECKED(holder, name, offset, condition)   \
280    int holder::name() const {                                     \
281      DCHECK(condition);                                           \
282      Smi value = TaggedField<Smi, offset>::load(*this);           \
283      return value.value();                                        \
284    }                                                              \
285    void holder::set_##name(int value) {                           \
286      DCHECK(condition);                                           \
287      TaggedField<Smi, offset>::store(*this, Smi::FromInt(value)); \
288    }
289  
290  #define SMI_ACCESSORS(holder, name, offset) \
291    SMI_ACCESSORS_CHECKED(holder, name, offset, true)
292  
293  #define SYNCHRONIZED_SMI_ACCESSORS(holder, name, offset)                 \
294    int holder::synchronized_##name() const {                              \
295      Smi value = TaggedField<Smi, offset>::Acquire_Load(*this);           \
296      return value.value();                                                \
297    }                                                                      \
298    void holder::synchronized_set_##name(int value) {                      \
299      TaggedField<Smi, offset>::Release_Store(*this, Smi::FromInt(value)); \
300    }
301  
302  #define RELAXED_SMI_ACCESSORS(holder, name, offset)                      \
303    int holder::relaxed_read_##name() const {                              \
304      Smi value = TaggedField<Smi, offset>::Relaxed_Load(*this);           \
305      return value.value();                                                \
306    }                                                                      \
307    void holder::relaxed_write_##name(int value) {                         \
308      TaggedField<Smi, offset>::Relaxed_Store(*this, Smi::FromInt(value)); \
309    }
310  
311  #define BOOL_GETTER(holder, field, name, offset) \
312    bool holder::name() const { return BooleanBit::get(field(), offset); }
313  
314  #define BOOL_ACCESSORS(holder, field, name, offset)                      \
315    bool holder::name() const { return BooleanBit::get(field(), offset); } \
316    void holder::set_##name(bool value) {                                  \
317      set_##field(BooleanBit::set(field(), offset, value));                \
318    }
319  
320  #define BIT_FIELD_ACCESSORS(holder, field, name, BitField)      \
321    typename BitField::FieldType holder::name() const {           \
322      return BitField::decode(field());                           \
323    }                                                             \
324    void holder::set_##name(typename BitField::FieldType value) { \
325      set_##field(BitField::update(field(), value));              \
326    }
327  
328  #define INSTANCE_TYPE_CHECKER(type, forinstancetype)    \
329    V8_INLINE bool Is##type(InstanceType instance_type) { \
330      return instance_type == forinstancetype;            \
331    }
332  
333  #define TYPE_CHECKER(type, ...)                                         \
334    DEF_GETTER(HeapObject, Is##type, bool) {                              \
335      return InstanceTypeChecker::Is##type(map(isolate).instance_type()); \
336    }
337  
338  #define RELAXED_INT16_ACCESSORS(holder, name, offset) \
339    int16_t holder::name() const {                      \
340      return RELAXED_READ_INT16_FIELD(*this, offset);   \
341    }                                                   \
342    void holder::set_##name(int16_t value) {            \
343      RELAXED_WRITE_INT16_FIELD(*this, offset, value);  \
344    }
345  
346  #define FIELD_ADDR(p, offset) ((p).ptr() + offset - kHeapObjectTag)
347  
348  #define ACQUIRE_READ_FIELD(p, offset) \
349    TaggedField<Object>::Acquire_Load(p, offset)
350  
351  #define RELAXED_READ_FIELD(p, offset) \
352    TaggedField<Object>::Relaxed_Load(p, offset)
353  
354  #define RELAXED_READ_WEAK_FIELD(p, offset) \
355    TaggedField<MaybeObject>::Relaxed_Load(p, offset)
356  
357  #define WRITE_FIELD(p, offset, value) \
358    TaggedField<Object>::store(p, offset, value)
359  
360  #define RELEASE_WRITE_FIELD(p, offset, value) \
361    TaggedField<Object>::Release_Store(p, offset, value)
362  
363  #define RELAXED_WRITE_FIELD(p, offset, value) \
364    TaggedField<Object>::Relaxed_Store(p, offset, value)
365  
366  #define RELAXED_WRITE_WEAK_FIELD(p, offset, value) \
367    TaggedField<MaybeObject>::Relaxed_Store(p, offset, value)
368  
369  #ifdef V8_DISABLE_WRITE_BARRIERS
370  #define WRITE_BARRIER(object, offset, value)
371  #else
372  #define WRITE_BARRIER(object, offset, value)                         \
373    do {                                                               \
374      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));              \
375      WriteBarrier::Marking(object, (object).RawField(offset), value); \
376      GenerationalBarrier(object, (object).RawField(offset), value);   \
377    } while (false)
378  #endif
379  
380  #ifdef V8_DISABLE_WRITE_BARRIERS
381  #define WEAK_WRITE_BARRIER(object, offset, value)
382  #else
383  #define WEAK_WRITE_BARRIER(object, offset, value)                             \
384    do {                                                                        \
385      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));                       \
386      WriteBarrier::Marking(object, (object).RawMaybeWeakField(offset), value); \
387      GenerationalBarrier(object, (object).RawMaybeWeakField(offset), value);   \
388    } while (false)
389  #endif
390  
391  #ifdef V8_DISABLE_WRITE_BARRIERS
392  #define EPHEMERON_KEY_WRITE_BARRIER(object, offset, value)
393  #elif V8_ENABLE_UNCONDITIONAL_WRITE_BARRIERS
394  #define EPHEMERON_KEY_WRITE_BARRIER(object, offset, value) \
395    WRITE_BARRIER(object, offset, value)
396  #else
397  #define EPHEMERON_KEY_WRITE_BARRIER(object, offset, value)                    \
398    do {                                                                        \
399      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));                       \
400      EphemeronHashTable table = EphemeronHashTable::cast(object);              \
401      WriteBarrier::Marking(object, (object).RawField(offset), value);          \
402      GenerationalEphemeronKeyBarrier(table, (object).RawField(offset), value); \
403    } while (false)
404  #endif
405  
406  #ifdef V8_DISABLE_WRITE_BARRIERS
407  #define CONDITIONAL_WRITE_BARRIER(object, offset, value, mode)
408  #elif V8_ENABLE_UNCONDITIONAL_WRITE_BARRIERS
409  #define CONDITIONAL_WRITE_BARRIER(object, offset, value, mode) \
410    WRITE_BARRIER(object, offset, value)
411  #else
412  #define CONDITIONAL_WRITE_BARRIER(object, offset, value, mode)           \
413    do {                                                                   \
414      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));                  \
415      DCHECK_NE(mode, UPDATE_EPHEMERON_KEY_WRITE_BARRIER);                 \
416      if (mode != SKIP_WRITE_BARRIER) {                                    \
417        if (mode == UPDATE_WRITE_BARRIER) {                                \
418          WriteBarrier::Marking(object, (object).RawField(offset), value); \
419        }                                                                  \
420        GenerationalBarrier(object, (object).RawField(offset), value);     \
421      }                                                                    \
422    } while (false)
423  #endif
424  
425  #ifdef V8_DISABLE_WRITE_BARRIERS
426  #define CONDITIONAL_WEAK_WRITE_BARRIER(object, offset, value, mode)
427  #elif V8_ENABLE_UNCONDITIONAL_WRITE_BARRIERS
428  #define CONDITIONAL_WEAK_WRITE_BARRIER(object, offset, value, mode) \
429    WRITE_BARRIER(object, offset, value)
430  #else
431  #define CONDITIONAL_WEAK_WRITE_BARRIER(object, offset, value, mode)           \
432    do {                                                                        \
433      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));                       \
434      DCHECK_NE(mode, UPDATE_EPHEMERON_KEY_WRITE_BARRIER);                      \
435      if (mode != SKIP_WRITE_BARRIER) {                                         \
436        if (mode == UPDATE_WRITE_BARRIER) {                                     \
437          WriteBarrier::Marking(object, (object).RawMaybeWeakField(offset),     \
438                                value);                                         \
439        }                                                                       \
440        GenerationalBarrier(object, (object).RawMaybeWeakField(offset), value); \
441      }                                                                         \
442    } while (false)
443  #endif
444  
445  #ifdef V8_DISABLE_WRITE_BARRIERS
446  #define CONDITIONAL_EPHEMERON_KEY_WRITE_BARRIER(object, offset, value, mode)
447  #else
448  #define CONDITIONAL_EPHEMERON_KEY_WRITE_BARRIER(object, offset, value, mode) \
449    do {                                                                       \
450      DCHECK_NOT_NULL(GetHeapFromWritableObject(object));                      \
451      DCHECK_NE(mode, UPDATE_EPHEMERON_KEY_WRITE_BARRIER);                     \
452      EphemeronHashTable table = EphemeronHashTable::cast(object);             \
453      if (mode != SKIP_WRITE_BARRIER) {                                        \
454        if (mode == UPDATE_WRITE_BARRIER) {                                    \
455          WriteBarrier::Marking(object, (object).RawField(offset), value);     \
456        }                                                                      \
457        GenerationalEphemeronKeyBarrier(table, (object).RawField(offset),      \
458                                        value);                                \
459      }                                                                        \
460    } while (false)
461  #endif
462  
463  #define ACQUIRE_READ_INT32_FIELD(p, offset) \
464    static_cast<int32_t>(base::Acquire_Load(  \
465        reinterpret_cast<const base::Atomic32*>(FIELD_ADDR(p, offset))))
466  
467  #define RELAXED_WRITE_INT8_FIELD(p, offset, value)                             \
468    base::Relaxed_Store(reinterpret_cast<base::Atomic8*>(FIELD_ADDR(p, offset)), \
469                        static_cast<base::Atomic8>(value));
470  #define RELAXED_READ_INT8_FIELD(p, offset) \
471    static_cast<int8_t>(base::Relaxed_Load(  \
472        reinterpret_cast<const base::Atomic8*>(FIELD_ADDR(p, offset))))
473  
474  #define RELAXED_READ_INT16_FIELD(p, offset) \
475    static_cast<int16_t>(base::Relaxed_Load(  \
476        reinterpret_cast<const base::Atomic16*>(FIELD_ADDR(p, offset))))
477  
478  #define RELAXED_WRITE_INT16_FIELD(p, offset, value)             \
479    base::Relaxed_Store(                                          \
480        reinterpret_cast<base::Atomic16*>(FIELD_ADDR(p, offset)), \
481        static_cast<base::Atomic16>(value));
482  
483  #define RELAXED_READ_UINT32_FIELD(p, offset) \
484    static_cast<uint32_t>(base::Relaxed_Load(  \
485        reinterpret_cast<const base::Atomic32*>(FIELD_ADDR(p, offset))))
486  
487  #define RELAXED_WRITE_UINT32_FIELD(p, offset, value)            \
488    base::Relaxed_Store(                                          \
489        reinterpret_cast<base::Atomic32*>(FIELD_ADDR(p, offset)), \
490        static_cast<base::Atomic32>(value));
491  
492  #define RELAXED_READ_INT32_FIELD(p, offset) \
493    static_cast<int32_t>(base::Relaxed_Load(  \
494        reinterpret_cast<const base::Atomic32*>(FIELD_ADDR(p, offset))))
495  
496  #define RELEASE_WRITE_INT32_FIELD(p, offset, value)             \
497    base::Release_Store(                                          \
498        reinterpret_cast<base::Atomic32*>(FIELD_ADDR(p, offset)), \
499        static_cast<base::Atomic32>(value))
500  
501  #define RELAXED_WRITE_INT32_FIELD(p, offset, value)             \
502    base::Relaxed_Store(                                          \
503        reinterpret_cast<base::Atomic32*>(FIELD_ADDR(p, offset)), \
504        static_cast<base::Atomic32>(value));
505  
506  #define RELAXED_READ_BYTE_FIELD(p, offset) \
507    static_cast<byte>(base::Relaxed_Load(    \
508        reinterpret_cast<const base::Atomic8*>(FIELD_ADDR(p, offset))))
509  
510  #define RELAXED_WRITE_BYTE_FIELD(p, offset, value)                             \
511    base::Relaxed_Store(reinterpret_cast<base::Atomic8*>(FIELD_ADDR(p, offset)), \
512                        static_cast<base::Atomic8>(value));
513  
514  #ifdef OBJECT_PRINT
515  #define DECL_PRINTER(Name) void Name##Print(std::ostream& os);  // NOLINT
516  #else
517  #define DECL_PRINTER(Name)
518  #endif
519  
520  #ifdef VERIFY_HEAP
521  #define DECL_VERIFIER(Name) void Name##Verify(Isolate* isolate);
522  #define EXPORT_DECL_VERIFIER(Name) \
523    V8_EXPORT_PRIVATE void Name##Verify(Isolate* isolate);
524  #else
525  #define DECL_VERIFIER(Name)
526  #define EXPORT_DECL_VERIFIER(Name)
527  #endif
528  
529  #define DEFINE_DEOPT_ELEMENT_ACCESSORS(name, type) \
530    type DeoptimizationData::name() const {          \
531      return type::cast(get(k##name##Index));        \
532    }                                                \
533    void DeoptimizationData::Set##name(type value) { set(k##name##Index, value); }
534  
535  #define DEFINE_DEOPT_ENTRY_ACCESSORS(name, type)                \
536    type DeoptimizationData::name(int i) const {                  \
537      return type::cast(get(IndexForEntry(i) + k##name##Offset)); \
538    }                                                             \
539    void DeoptimizationData::Set##name(int i, type value) {       \
540      set(IndexForEntry(i) + k##name##Offset, value);             \
541    }
542  
543  #define TQ_OBJECT_CONSTRUCTORS(Type)               \
544   public:                                           \
545    constexpr Type() = default;                      \
546                                                     \
547   protected:                                        \
548    template <typename TFieldType, int kFieldOffset> \
549    friend class TaggedField;                        \
550                                                     \
551    inline explicit Type(Address ptr);               \
552    friend class TorqueGenerated##Type<Type, Super>;
553  
554  #define TQ_OBJECT_CONSTRUCTORS_IMPL(Type) \
555    inline Type::Type(Address ptr)          \
556        : TorqueGenerated##Type<Type, Type::Super>(ptr) {}
557