10
10
#![ feature( const_mut_refs) ]
11
11
#![ feature( trivial_bounds) ]
12
12
13
+ mod arena;
14
+ mod auto_traits;
15
+ mod gc;
13
16
mod mark;
17
+ mod trace;
18
+
19
+ use arena:: * ;
20
+ use auto_traits:: * ;
21
+ use gc:: * ;
22
+ use mark:: * ;
23
+ use trace:: * ;
14
24
15
- use std:: cell:: UnsafeCell ;
16
25
use std:: collections:: HashMap ;
17
- use std:: collections:: HashSet ;
18
- use std:: mem:: * ;
19
- use std:: ops:: Deref ;
20
- use std:: ptr;
21
26
use std:: sync:: Mutex ;
22
27
use std:: thread_local;
23
28
24
- pub unsafe trait Trace {
25
- fn trace ( t : & Self ) ;
26
- const TRACE_TYPE_INFO : GcTypeInfo ;
27
- const TRACE_CHILD_TYPE_INFO : [ Option < GcTypeInfo > ; 8 ] ;
28
- fn trace_transitive_type_info ( tti : & mut Tti ) ;
29
- }
30
-
31
- pub struct Tti {
32
- /// Holds fn ptr of trace_transitive_type_info calls
33
- parrents : HashSet < usize > ,
34
- type_info : HashSet < GcTypeInfo > ,
35
- }
36
-
37
- impl Tti {
38
- pub fn new ( ) -> Self {
39
- Self {
40
- parrents : HashSet :: new ( ) ,
41
- type_info : HashSet :: new ( ) ,
42
- }
43
- }
44
-
45
- pub fn add_direct < T : Trace > ( & mut self ) {
46
- self . type_info
47
- . extend ( T :: TRACE_CHILD_TYPE_INFO . iter ( ) . filter_map ( |o| * o) ) ;
48
- }
49
-
50
- pub fn add_trans ( & mut self , tti : fn ( & mut Tti ) ) {
51
- if self . parrents . insert ( tti as * const fn ( & mut Tti ) as usize ) {
52
- tti ( self )
53
- }
54
- }
55
- }
56
-
57
- #[ derive( Debug , Copy , Clone , PartialEq , Eq , PartialOrd , Ord , Hash ) ]
58
- pub struct GcTypeInfo {
59
- trace_ptr : usize ,
60
- drop_ptr : usize ,
61
- needs_drop : bool ,
62
- byte_size : u16 ,
63
- alignment : u16 ,
64
- }
65
-
66
- impl GcTypeInfo {
67
- pub const fn new < T : Trace > ( ) -> Self {
68
- Self {
69
- trace_ptr : unsafe { T :: trace as * const fn ( & T ) as usize } ,
70
- drop_ptr : unsafe { ptr:: drop_in_place :: < T > as * const fn ( * mut T ) as usize } ,
71
- needs_drop : needs_drop :: < T > ( ) ,
72
- byte_size : size_of :: < T > ( ) as u16 ,
73
- alignment : align_of :: < T > ( ) as u16 ,
74
- }
75
- }
76
-
77
- pub ( crate ) const fn one_child < T : Trace > ( ) -> [ Option < GcTypeInfo > ; 8 ] {
78
- [
79
- Some ( GcTypeInfo :: new :: < T > ( ) ) ,
80
- None ,
81
- None ,
82
- None ,
83
- None ,
84
- None ,
85
- None ,
86
- None ,
87
- ]
88
- }
89
- }
90
-
91
- #[ derive( Debug , Copy , Clone , PartialEq , Eq , PartialOrd , Ord ) ]
92
- pub struct Gc < ' r , T > {
93
- ptr : & ' r T ,
94
- }
95
-
96
- impl < ' r , T : Trace > Deref for Gc < ' r , T > {
97
- type Target = T ;
98
- fn deref ( & self ) -> & T {
99
- self . ptr
100
- }
101
- }
102
-
103
29
thread_local ! {
104
30
/// Map from type to GC communication bus.
105
31
static GC_BUS : HashMap <GcTypeInfo , Box <Mutex <BusMsg >>> = HashMap :: new( ) ;
@@ -118,119 +44,6 @@ struct BusMsg {
118
44
grey_feilds : u16 ,
119
45
}
120
46
121
- pub struct Arena < T > {
122
- // roots: usize,
123
- high_ptr : * const T ,
124
- capacity : u16 ,
125
- }
126
-
127
- impl < T : Trace > Arena < T > {
128
- pub fn new ( ) -> Self {
129
- // GC_BUS.with(|type_map| T::TRACE_TYPE_INFOtype_map.entry());
130
- Self {
131
- high_ptr : ptr:: null ( ) ,
132
- capacity : 1000 ,
133
- }
134
- }
135
- pub fn gc_alloc < ' r > ( & ' r self , _t : T ) -> Gc < ' r , T >
136
- where
137
- T : ' r ,
138
- {
139
- unimplemented ! ( )
140
- }
141
-
142
- pub fn advance ( & mut self ) -> Self {
143
- unimplemented ! ( )
144
- }
145
- }
146
-
147
- // Auto traits
148
- pub unsafe auto trait HasNoGc { }
149
- impl < ' r , T > !HasNoGc for Gc < ' r , T > { }
150
- unsafe impl < ' r , T : HasNoGc > HasNoGc for Box < T > { }
151
-
152
- /// Shallow immutability
153
- pub unsafe auto trait Immutable { }
154
- impl < T > !Immutable for & mut T { }
155
- impl < T > !Immutable for UnsafeCell < T > { }
156
- unsafe impl < T > Immutable for Box < T > { }
157
-
158
- // Needs negative impls
159
- // TODO Blanket impl seems to be safe, since Mark's blanket requires HasNoGc
160
- // If you only implement Mark and not Trace CHILD_TYPE_INFO will all be const None
161
- unsafe impl < T : Immutable > Trace for T {
162
- default fn trace ( _: & T ) { }
163
- default const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new:: < Self > ( ) ;
164
- default const TRACE_CHILD_TYPE_INFO : [ Option <GcTypeInfo >; 8 ] = [ None ; 8 ] ;
165
- default fn trace_transitive_type_info ( _: & mut Tti ) { }
166
- }
167
-
168
- unsafe impl < ' o , ' n , T : HasNoGc + Immutable > Mark < ' o , ' n , T , T > for Arena < T > {
169
- fn mark ( & ' n self , o : Gc < ' o , T > ) -> Gc < ' n , T > {
170
- unsafe { std:: mem:: transmute ( o) }
171
- }
172
- }
173
-
174
- unsafe impl < ' r , T : ' r + Immutable + Trace > Trace for Gc < ' r , T > {
175
- fn trace ( t : & Self ) {
176
- Trace :: trace ( t. deref ( ) )
177
- }
178
- // A Gc<Gc<T>> is equvlent to Gc<T>
179
- const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new :: < T > ( ) ;
180
- const TRACE_CHILD_TYPE_INFO : [ Option < GcTypeInfo > ; 8 ] = [
181
- Some ( GcTypeInfo :: new :: < T > ( ) ) ,
182
- None ,
183
- None ,
184
- None ,
185
- None ,
186
- None ,
187
- None ,
188
- None ,
189
- ] ;
190
- fn trace_transitive_type_info ( tti : & mut Tti ) {
191
- tti. add_direct :: < Self > ( ) ;
192
- T :: trace_transitive_type_info ( tti)
193
- }
194
- }
195
-
196
- unsafe impl < ' r , T : Immutable + Trace > Trace for Option < T > {
197
- default fn trace ( t : & Self ) {
198
- Trace :: trace ( t. deref ( ) )
199
- }
200
- default const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new:: < Self > ( ) ;
201
- default const TRACE_CHILD_TYPE_INFO : [ Option <GcTypeInfo >; 8 ] = GcTypeInfo :: one_child:: < T > ( ) ;
202
- default fn trace_transitive_type_info ( tti : & mut Tti ) {
203
- tti. add_direct :: < Self > ( ) ;
204
- tti. add_trans ( T :: trace_transitive_type_info) ;
205
- }
206
- }
207
-
208
- unsafe impl < ' r , T : Immutable + Trace + HasNoGc > Trace for Option < T > {
209
- fn trace ( t : & Self ) {
210
- Trace :: trace ( t. deref ( ) )
211
- }
212
- const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new :: < Self > ( ) ;
213
- const TRACE_CHILD_TYPE_INFO : [ Option < GcTypeInfo > ; 8 ] = [ None ; 8 ] ;
214
- fn trace_transitive_type_info ( _: & mut Tti ) { }
215
- }
216
-
217
- unsafe impl < T : Immutable + Trace > Trace for Box < T > {
218
- default fn trace ( _: & Self ) { }
219
- default const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new:: < Self > ( ) ;
220
- default const TRACE_CHILD_TYPE_INFO : [ Option <GcTypeInfo >; 8 ] = [ None ; 8 ] ;
221
- default fn trace_transitive_type_info ( _: & mut Tti ) { }
222
- }
223
-
224
- unsafe impl < T : Immutable + Trace + HasNoGc > Trace for Box < T > {
225
- fn trace ( _: & Self ) { }
226
- const TRACE_TYPE_INFO : GcTypeInfo = GcTypeInfo :: new :: < Self > ( ) ;
227
- const TRACE_CHILD_TYPE_INFO : [ Option < GcTypeInfo > ; 8 ] = GcTypeInfo :: one_child :: < T > ( ) ;
228
- fn trace_transitive_type_info ( tti : & mut Tti ) {
229
- tti. add_direct :: < Self > ( ) ;
230
- tti. add_trans ( T :: trace_transitive_type_info) ;
231
- }
232
- }
233
-
234
47
// #[derive(Trace, Mark)
235
48
struct List < ' r , T > {
236
49
_t : T ,
@@ -259,9 +72,7 @@ unsafe impl<'r, T: 'r + Trace + Immutable> Trace for List<'r, T> {
259
72
}
260
73
}
261
74
262
- unsafe impl < ' o , ' n , T : Trace + HasNoGc > Mark < ' o , ' n , List < ' o , T > , List < ' n , T > >
263
- for Arena < List < ' n , T > >
264
- {
75
+ unsafe impl < ' o , ' n , T : Trace + NoGc > Mark < ' o , ' n , List < ' o , T > , List < ' n , T > > for Arena < List < ' n , T > > {
265
76
fn mark ( & ' n self , o : Gc < ' o , List < ' o , T > > ) -> Gc < ' n , List < ' n , T > > {
266
77
unsafe { std:: mem:: transmute ( o) }
267
78
}
0 commit comments