1 // Copyright 2017 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_LABEL_H_ 6 #define V8_LABEL_H_ 7 8 #include "src/base/macros.h" 9 10 namespace v8 { 11 namespace internal { 12 13 // ----------------------------------------------------------------------------- 14 // Labels represent pc locations; they are typically jump or call targets. 15 // After declaration, a label can be freely used to denote known or (yet) 16 // unknown pc location. Assembler::bind() is used to bind a label to the 17 // current pc. A label can be bound only once. 18 19 class Label { 20 public: 21 enum Distance { kNear, kFar }; 22 INLINE(Label ())23 INLINE(Label()) { 24 Unuse(); 25 UnuseNear(); 26 } 27 INLINE(~Label ())28 INLINE(~Label()) { 29 DCHECK(!is_linked()); 30 DCHECK(!is_near_linked()); 31 } 32 INLINE(void Unuse ())33 INLINE(void Unuse()) { pos_ = 0; } INLINE(void UnuseNear ())34 INLINE(void UnuseNear()) { near_link_pos_ = 0; } 35 INLINE(bool is_bound ()const)36 INLINE(bool is_bound() const) { return pos_ < 0; } INLINE(bool is_unused ()const)37 INLINE(bool is_unused() const) { return pos_ == 0 && near_link_pos_ == 0; } INLINE(bool is_linked ()const)38 INLINE(bool is_linked() const) { return pos_ > 0; } INLINE(bool is_near_linked ()const)39 INLINE(bool is_near_linked() const) { return near_link_pos_ > 0; } 40 41 // Returns the position of bound or linked labels. Cannot be used 42 // for unused labels. pos()43 int pos() const { 44 if (pos_ < 0) return -pos_ - 1; 45 if (pos_ > 0) return pos_ - 1; 46 UNREACHABLE(); 47 return 0; 48 } 49 near_link_pos()50 int near_link_pos() const { return near_link_pos_ - 1; } 51 52 private: 53 // pos_ encodes both the binding state (via its sign) 54 // and the binding position (via its value) of a label. 55 // 56 // pos_ < 0 bound label, pos() returns the jump target position 57 // pos_ == 0 unused label 58 // pos_ > 0 linked label, pos() returns the last reference position 59 int pos_; 60 61 // Behaves like |pos_| in the "> 0" case, but for near jumps to this label. 62 int near_link_pos_; 63 bind_to(int pos)64 void bind_to(int pos) { 65 pos_ = -pos - 1; 66 DCHECK(is_bound()); 67 } 68 void link_to(int pos, Distance distance = kFar) { 69 if (distance == kNear) { 70 near_link_pos_ = pos + 1; 71 DCHECK(is_near_linked()); 72 } else { 73 pos_ = pos + 1; 74 DCHECK(is_linked()); 75 } 76 } 77 78 friend class Assembler; 79 friend class Displacement; 80 friend class RegExpMacroAssemblerIrregexp; 81 82 #if V8_TARGET_ARCH_ARM64 83 // On ARM64, the Assembler keeps track of pointers to Labels to resolve 84 // branches to distant targets. Copying labels would confuse the Assembler. 85 DISALLOW_COPY_AND_ASSIGN(Label); // NOLINT 86 #endif 87 }; 88 89 } // namespace internal 90 } // namespace v8 91 92 #endif // V8_LABEL_H_ 93