• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===----------------------------------------------------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 #ifndef SUPPORT_TRACKED_VALUE_H
10 #define SUPPORT_TRACKED_VALUE_H
11 
12 #include <cassert>
13 
14 struct TrackedValue {
15     enum State { CONSTRUCTED, MOVED_FROM, DESTROYED };
16     State state;
17 
TrackedValueTrackedValue18     TrackedValue() : state(State::CONSTRUCTED) {}
19 
TrackedValueTrackedValue20     TrackedValue(TrackedValue const& t) : state(State::CONSTRUCTED) {
21         assert(t.state != State::MOVED_FROM && "copying a moved-from object");
22         assert(t.state != State::DESTROYED  && "copying a destroyed object");
23     }
24 
25 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
TrackedValueTrackedValue26     TrackedValue(TrackedValue&& t) : state(State::CONSTRUCTED) {
27         assert(t.state != State::MOVED_FROM && "double moving from an object");
28         assert(t.state != State::DESTROYED  && "moving from a destroyed object");
29         t.state = State::MOVED_FROM;
30     }
31 #endif
32 
33     TrackedValue& operator=(TrackedValue const& t) {
34         assert(state != State::DESTROYED && "copy assigning into destroyed object");
35         assert(t.state != State::MOVED_FROM && "copying a moved-from object");
36         assert(t.state != State::DESTROYED  && "copying a destroyed object");
37         state = t.state;
38         return *this;
39     }
40 
41 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
42     TrackedValue& operator=(TrackedValue&& t) {
43         assert(state != State::DESTROYED && "move assigning into destroyed object");
44         assert(t.state != State::MOVED_FROM && "double moving from an object");
45         assert(t.state != State::DESTROYED  && "moving from a destroyed object");
46         state = t.state;
47         t.state = State::MOVED_FROM;
48         return *this;
49     }
50 #endif
51 
~TrackedValueTrackedValue52     ~TrackedValue() {
53         assert(state != State::DESTROYED && "double-destroying an object");
54         state = State::DESTROYED;
55     }
56 };
57 
58 #endif // SUPPORT_TRACKED_VALUE_H
59