-
Notifications
You must be signed in to change notification settings - Fork 44
/
Copy pathObj.hpp
157 lines (126 loc) · 3.11 KB
/
Obj.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
#pragma once
#include <cassert>
#include <cstdio>
#include <cstdlib>
#include <memory>
#include <vector>
/// 错误断言,打印文件和行号,方便定位问题。
#define ASSERT(expr) \
((expr) || (fprintf(stderr, "asserted at %s:%d\n", __FILE__, __LINE__), \
abort(), \
false))
/// 错误中断,打印文件和行号,方便定位问题。
#define ABORT() \
(fprintf(stderr, "aborted at %s:%d\n", __FILE__, __LINE__), abort())
/// 对象系统基类
struct alignas(ptrdiff_t) Obj
{
struct Mgr;
struct Walked;
using Mark = void (*)(Obj* obj);
Obj() = default;
virtual ~Obj() = default;
template<typename T>
T* dcst()
{
return dynamic_cast<T*>(this);
}
template<typename T>
T* dcst() const
{
return dynamic_cast<T*>(this);
}
template<typename T>
T* scst()
{
return static_cast<T*>(this);
}
template<typename T>
T* scst() const
{
return static_cast<T*>(this);
}
template<typename T>
T& rcst()
{
return *reinterpret_cast<T*>(this);
}
template<typename T>
T& rcst() const
{
return *reinterpret_cast<T*>(this);
}
void* any{ nullptr }; /// 留给遍历器存放任意数据
template<typename T>
T* any_as()
{
return reinterpret_cast<T*>(any);
}
template<typename T>
T* any_as() const
{
return reinterpret_cast<T*>(any);
}
private:
Obj(Obj* next)
: __next__(next)
{
}
Obj(const Obj&) = delete;
Obj(Obj&&) = delete;
void operator=(const Obj&) = delete;
void operator=(Obj&&) = delete;
Obj* __next__{ nullptr }; /// 环形指针,低3位由于对齐要求必为0,用作标记
virtual void __mark__(Mark mark) = 0; /// 标记对象
};
/// 对象管理器
struct Obj::Mgr : Obj
{
Mgr()
: Obj(this)
{
}
template<typename T,
typename... Args,
typename = std::enable_if_t<std::is_convertible_v<T*, Obj*>>>
T* make(Args... args)
{
auto obj = new T(args...);
obj->__next__ = __next__, __next__ = obj;
return obj;
}
Obj* mRoot{ nullptr }; /// 根对象
/// 垃圾回收,使用标记-清扫算法
/// @warning 垃圾回收时调用栈上不能有对象的引用!
void gc();
private:
void __mark__(Mark mark) override;
static bool gc_marked(const Obj* obj)
{
return reinterpret_cast<uintptr_t>(obj->__next__) & uintptr_t(0b1);
}
static void gc_unmark(Obj* obj)
{
reinterpret_cast<uintptr_t&>(obj->__next__) &= ~uintptr_t(0b1);
}
static void gc_mark(Obj* obj)
{
reinterpret_cast<uintptr_t&>(obj->__next__) |= uintptr_t(0b1);
}
static void gc_mark_dfs(Obj* obj);
};
/// 检查循环引用,防止无限递归。
struct Obj::Walked
{
Obj* mObj;
Walked(Obj* obj)
: mObj(obj)
{
ASSERT((reinterpret_cast<uintptr_t>(mObj->__next__) & 0b10) == 0);
reinterpret_cast<uintptr_t&>(mObj->__next__) |= uintptr_t(0b10);
}
~Walked()
{
reinterpret_cast<uintptr_t&>(mObj->__next__) &= ~uintptr_t(0b10);
}
};