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_COMMON_PTR_COMPR_INL_H_
6 #define V8_COMMON_PTR_COMPR_INL_H_
7 
8 #include "include/v8-internal.h"
9 #include "src/common/ptr-compr.h"
10 #include "src/execution/isolate.h"
11 
12 namespace v8 {
13 namespace internal {
14 
15 #if V8_TARGET_ARCH_64_BIT
16 // Compresses full-pointer representation of a tagged value to on-heap
17 // representation.
CompressTagged(Address tagged)18 V8_INLINE Tagged_t CompressTagged(Address tagged) {
19   return static_cast<Tagged_t>(static_cast<uint32_t>(tagged));
20 }
21 
GetIsolateRoot(Address on_heap_addr)22 V8_INLINE Address GetIsolateRoot(Address on_heap_addr) {
23   // We subtract 1 here in order to let the compiler generate addition of 32-bit
24   // signed constant instead of 64-bit constant (the problem is that 2Gb looks
25   // like a negative 32-bit value). It's correct because we will never use
26   // leftmost address of V8 heap as |on_heap_addr|.
27   return RoundDown<kPtrComprIsolateRootAlignment>(on_heap_addr);
28 }
29 
GetIsolateRoot(const Isolate * isolate)30 V8_INLINE Address GetIsolateRoot(const Isolate* isolate) {
31   Address isolate_root = isolate->isolate_root();
32 #ifdef V8_COMPRESS_POINTERS
33   isolate_root = reinterpret_cast<Address>(V8_ASSUME_ALIGNED(
34       reinterpret_cast<void*>(isolate_root), kPtrComprIsolateRootAlignment));
35 #endif
36   return isolate_root;
37 }
38 
39 // Decompresses smi value.
DecompressTaggedSigned(Tagged_t raw_value)40 V8_INLINE Address DecompressTaggedSigned(Tagged_t raw_value) {
41   // For runtime code the upper 32-bits of the Smi value do not matter.
42   return static_cast<Address>(raw_value);
43 }
44 
45 // Decompresses weak or strong heap object pointer or forwarding pointer,
46 // preserving both weak- and smi- tags.
47 template <typename TOnHeapAddress>
DecompressTaggedPointer(TOnHeapAddress on_heap_addr,Tagged_t raw_value)48 V8_INLINE Address DecompressTaggedPointer(TOnHeapAddress on_heap_addr,
49                                           Tagged_t raw_value) {
50   return GetIsolateRoot(on_heap_addr) + static_cast<Address>(raw_value);
51 }
52 
53 // Decompresses any tagged value, preserving both weak- and smi- tags.
54 template <typename TOnHeapAddress>
DecompressTaggedAny(TOnHeapAddress on_heap_addr,Tagged_t raw_value)55 V8_INLINE Address DecompressTaggedAny(TOnHeapAddress on_heap_addr,
56                                       Tagged_t raw_value) {
57   return DecompressTaggedPointer(on_heap_addr, raw_value);
58 }
59 
60 #ifdef V8_COMPRESS_POINTERS
61 
62 STATIC_ASSERT(kPtrComprHeapReservationSize ==
63               Internals::kPtrComprHeapReservationSize);
64 STATIC_ASSERT(kPtrComprIsolateRootAlignment ==
65               Internals::kPtrComprIsolateRootAlignment);
66 
67 #endif  // V8_COMPRESS_POINTERS
68 
69 #else
70 
71 V8_INLINE Tagged_t CompressTagged(Address tagged) { UNREACHABLE(); }
72 
73 V8_INLINE Address DecompressTaggedSigned(Tagged_t raw_value) { UNREACHABLE(); }
74 
75 template <typename TOnHeapAddress>
76 V8_INLINE Address DecompressTaggedPointer(TOnHeapAddress on_heap_addr,
77                                           Tagged_t raw_value) {
78   UNREACHABLE();
79 }
80 
81 template <typename TOnHeapAddress>
82 V8_INLINE Address DecompressTaggedAny(TOnHeapAddress on_heap_addr,
83                                       Tagged_t raw_value) {
84   UNREACHABLE();
85 }
86 
87 #endif  // V8_TARGET_ARCH_64_BIT
88 }  // namespace internal
89 }  // namespace v8
90 
91 #endif  // V8_COMMON_PTR_COMPR_INL_H_
92