1 // Copyright 2020 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 // This file contains implementations of a few macros that are defined
6 // as external in Torque, so that generated debug code can work.
7
8 #ifndef V8_TORQUE_DEBUG_MACRO_SHIMS_H_
9 #define V8_TORQUE_DEBUG_MACRO_SHIMS_H_
10
11 #include "src/numbers/integer-literal.h"
12 #include "src/objects/smi.h"
13 #include "tools/debug_helper/debug-helper-internal.h"
14
15 // For Object::ReadField<T>.
16 #define READ_FIELD_OR_FAIL(Type, destination, accessor, object, offset) \
17 do { \
18 Type value{}; \
19 d::MemoryAccessResult validity = \
20 accessor(object - kHeapObjectTag + offset, \
21 reinterpret_cast<Type*>(&value), sizeof(value)); \
22 if (validity != d::MemoryAccessResult::kOk) return {validity, {}}; \
23 destination = value; \
24 } while (false)
25
26 // For TaggedField<T>::load.
27 #define READ_TAGGED_FIELD_OR_FAIL(destination, accessor, object, offset) \
28 do { \
29 Tagged_t value{}; \
30 d::MemoryAccessResult validity = \
31 accessor(object - kHeapObjectTag + offset, \
32 reinterpret_cast<uint8_t*>(&value), sizeof(value)); \
33 if (validity != d::MemoryAccessResult::kOk) return {validity, {}}; \
34 destination = EnsureDecompressed(value, object); \
35 } while (false)
36
37 // Process Value struct.
38 #define ASSIGN_OR_RETURN(dest, val) \
39 do { \
40 if ((val).validity != d::MemoryAccessResult::kOk) \
41 return {(val).validity, {}}; \
42 dest = (val).value; \
43 } while (false)
44
45 namespace v8 {
46 namespace internal {
47 namespace debug_helper_internal {
48 namespace TorqueDebugMacroShims {
49 namespace CodeStubAssembler {
50
BoolConstant(d::MemoryAccessor accessor,bool b)51 inline Value<bool> BoolConstant(d::MemoryAccessor accessor, bool b) {
52 return {d::MemoryAccessResult::kOk, b};
53 }
ChangeInt32ToIntPtr(d::MemoryAccessor accessor,int32_t i)54 inline Value<intptr_t> ChangeInt32ToIntPtr(d::MemoryAccessor accessor,
55 int32_t i) {
56 return {d::MemoryAccessResult::kOk, i};
57 }
ChangeUint32ToWord(d::MemoryAccessor accessor,uint32_t u)58 inline Value<uintptr_t> ChangeUint32ToWord(d::MemoryAccessor accessor,
59 uint32_t u) {
60 return {d::MemoryAccessResult::kOk, u};
61 }
IntPtrAdd(d::MemoryAccessor accessor,intptr_t a,intptr_t b)62 inline Value<intptr_t> IntPtrAdd(d::MemoryAccessor accessor, intptr_t a,
63 intptr_t b) {
64 return {d::MemoryAccessResult::kOk, a + b};
65 }
IntPtrMul(d::MemoryAccessor accessor,intptr_t a,intptr_t b)66 inline Value<intptr_t> IntPtrMul(d::MemoryAccessor accessor, intptr_t a,
67 intptr_t b) {
68 return {d::MemoryAccessResult::kOk, a * b};
69 }
IntPtrLessThan(d::MemoryAccessor accessor,intptr_t a,intptr_t b)70 inline Value<bool> IntPtrLessThan(d::MemoryAccessor accessor, intptr_t a,
71 intptr_t b) {
72 return {d::MemoryAccessResult::kOk, a < b};
73 }
IntPtrLessThanOrEqual(d::MemoryAccessor accessor,intptr_t a,intptr_t b)74 inline Value<bool> IntPtrLessThanOrEqual(d::MemoryAccessor accessor, intptr_t a,
75 intptr_t b) {
76 return {d::MemoryAccessResult::kOk, a <= b};
77 }
Signed(d::MemoryAccessor accessor,uintptr_t u)78 inline Value<intptr_t> Signed(d::MemoryAccessor accessor, uintptr_t u) {
79 return {d::MemoryAccessResult::kOk, static_cast<intptr_t>(u)};
80 }
SmiUntag(d::MemoryAccessor accessor,uintptr_t s_t)81 inline Value<int32_t> SmiUntag(d::MemoryAccessor accessor, uintptr_t s_t) {
82 Smi s(s_t);
83 return {d::MemoryAccessResult::kOk, s.value()};
84 }
SmiFromInt32(d::MemoryAccessor accessor,int32_t i)85 inline Value<uintptr_t> SmiFromInt32(d::MemoryAccessor accessor, int32_t i) {
86 return {d::MemoryAccessResult::kOk, Smi::FromInt(i).ptr()};
87 }
UintPtrLessThan(d::MemoryAccessor accessor,uintptr_t a,uintptr_t b)88 inline Value<bool> UintPtrLessThan(d::MemoryAccessor accessor, uintptr_t a,
89 uintptr_t b) {
90 return {d::MemoryAccessResult::kOk, a < b};
91 }
Unsigned(d::MemoryAccessor accessor,int32_t s)92 inline Value<uint32_t> Unsigned(d::MemoryAccessor accessor, int32_t s) {
93 return {d::MemoryAccessResult::kOk, static_cast<uint32_t>(s)};
94 }
95 #if V8_HOST_ARCH_64_BIT
Unsigned(d::MemoryAccessor accessor,intptr_t s)96 inline Value<uintptr_t> Unsigned(d::MemoryAccessor accessor, intptr_t s) {
97 return {d::MemoryAccessResult::kOk, static_cast<uintptr_t>(s)};
98 }
99 #endif
Word32Equal(d::MemoryAccessor accessor,uint32_t a,uint32_t b)100 inline Value<bool> Word32Equal(d::MemoryAccessor accessor, uint32_t a,
101 uint32_t b) {
102 return {d::MemoryAccessResult::kOk, a == b};
103 }
Word32NotEqual(d::MemoryAccessor accessor,uint32_t a,uint32_t b)104 inline Value<bool> Word32NotEqual(d::MemoryAccessor accessor, uint32_t a,
105 uint32_t b) {
106 return {d::MemoryAccessResult::kOk, a != b};
107 }
108 // This is used in a nested call where we cannot pass Value<int32_t>.
ConstexprIntegerLiteralToInt31(d::MemoryAccessor accessor,const IntegerLiteral & i)109 inline int31_t ConstexprIntegerLiteralToInt31(d::MemoryAccessor accessor,
110 const IntegerLiteral& i) {
111 return i.To<int32_t>();
112 }
ConstexprIntegerLiteralToInt32(d::MemoryAccessor accessor,const IntegerLiteral & i)113 inline int32_t ConstexprIntegerLiteralToInt32(d::MemoryAccessor accessor,
114 const IntegerLiteral& i) {
115 return i.To<int32_t>();
116 }
ConstexprIntegerLiteralToIntptr(d::MemoryAccessor accessor,const IntegerLiteral & i)117 inline intptr_t ConstexprIntegerLiteralToIntptr(d::MemoryAccessor accessor,
118 const IntegerLiteral& i) {
119 return i.To<intptr_t>();
120 }
121
122 } // namespace CodeStubAssembler
123 } // namespace TorqueDebugMacroShims
124 } // namespace debug_helper_internal
125 } // namespace internal
126 } // namespace v8
127
128 #endif // V8_TORQUE_DEBUG_MACRO_SHIMS_H_
129