@@ -22,37 +22,28 @@ class arena {
22
22
initialize_semispace ();
23
23
}
24
24
25
+ char *evacuate (char *scan_ptr);
26
+
25
27
// Allocates the requested number of bytes as a contiguous region and returns a
26
28
// pointer to the first allocated byte.
27
29
void *kore_arena_alloc (size_t requested);
28
30
29
31
// Returns the address of the first byte that belongs in the given arena.
30
- // Returns 0 if nothing has been allocated ever in that arena.
31
- char *arena_start_ptr () const {
32
- return current_addr_ptr ? current_addr_ptr + sizeof (memory_block_header)
33
- : nullptr ;
34
- }
32
+ // Returns nullptr if nothing has been allocated ever in that arena.
33
+ char *arena_start_ptr () const { return current_addr_ptr; }
35
34
36
35
// Returns a pointer to a location holding the address of last allocated
37
36
// byte in the given arena plus 1.
38
- // This address is 0 if nothing has been allocated ever in that arena.
39
- char **arena_end_ptr () { return &allocation_ptr; }
40
-
41
- // return the total number of allocatable bytes currently in the arena in its
42
- // active semispace.
43
- size_t arena_size () const {
44
- update_num_blocks ();
45
- return BLOCK_SIZE * std::max (num_blocks, num_collection_blocks);
46
- }
37
+ // This address is nullptr if nothing has been allocated ever in that arena.
38
+ char *arena_end_ptr () { return allocation_ptr; }
47
39
48
40
// Clears the current allocation space by setting its start back to its first
49
41
// block. It is used during garbage collection to effectively collect all of the
50
- // arena.
42
+ // arena. Resets the tripwire.
51
43
void arena_clear ();
52
44
53
- // Resizes the last allocation as long as the resize does not require a new
54
- // block allocation.
55
- // Returns the address of the byte following the last newlly allocated byte.
45
+ // Resizes the last allocation.
46
+ // Returns the address of the byte following the last newly allocated byte.
56
47
void *arena_resize_last_alloc (ssize_t increase) {
57
48
return (allocation_ptr += increase);
58
49
}
@@ -71,10 +62,8 @@ class arena {
71
62
void arena_swap_and_clear ();
72
63
73
64
// Given two pointers to objects allocated in the same arena, return the number
74
- // of bytes they are separated by within the virtual block of memory represented
75
- // by the blocks of that arena. This difference will include blocks containing
76
- // sentinel bytes. Undefined behavior will result if the pointers belong to
77
- // different arenas.
65
+ // of bytes they are apart. Undefined behavior will result if the pointers
66
+ // don't belong to the same arena
78
67
static ssize_t ptr_diff (char *ptr1, char *ptr2) { return ptr1 - ptr2; }
79
68
80
69
// Given a starting pointer to an address allocated in an arena and a size in
@@ -84,11 +73,11 @@ class arena {
84
73
// 1st argument: the starting pointer
85
74
// 2nd argument: the size in bytes to add to the starting pointer
86
75
// 3rd argument: the address of last allocated byte in the arena plus 1
87
- // Return value: the address allocated in the arena after size bytes from the
88
- // starting pointer, or 0 if this is equal to the 3rd argument.
89
- static char *move_ptr (char *ptr, size_t size, char const *arena_end_ptr ) {
76
+ // Return value: starting pointer + size unless this points to unallocated space
77
+ // in which case nullptr is returned
78
+ static char *move_ptr (char *ptr, size_t size, char const *end_ptr ) {
90
79
char *next_ptr = ptr + size;
91
- return (next_ptr == arena_end_ptr ) ? 0 : next_ptr;
80
+ return (next_ptr == end_ptr ) ? nullptr : next_ptr;
92
81
}
93
82
94
83
// Returns the ID of the semispace where the given address was allocated.
@@ -97,15 +86,6 @@ class arena {
97
86
static char get_arena_semispace_id_of_object (void *ptr);
98
87
99
88
private:
100
- union memory_block_header {
101
- //
102
- // Currently the header just holds the semispace id. But we need it to be a
103
- // multiple of sizeof(char*) for alignment purposes so we add a dummy char*.
104
- //
105
- char semispace;
106
- char *alignment_dummy;
107
- };
108
-
109
89
//
110
90
// We update the number of 1MB blocks actually written to, only when we need this value,
111
91
// or before a garbage collection rather than trying to determine when we write to a fresh block.
@@ -121,13 +101,6 @@ class arena {
121
101
}
122
102
123
103
void initialize_semispace ();
124
-
125
- static memory_block_header *mem_block_header (void *ptr) {
126
- uintptr_t address = reinterpret_cast <uintptr_t >(ptr);
127
- return reinterpret_cast <arena::memory_block_header *>(
128
- (address - 1 ) & ~(HYPERBLOCK_SIZE - 1 ));
129
- }
130
-
131
104
//
132
105
// Current semispace where allocations are being made.
133
106
//
@@ -146,9 +119,22 @@ class arena {
146
119
= 0 ; // notional number of BLOCK_SIZE blocks in collection semispace
147
120
};
148
121
122
+ inline char arena::get_arena_semispace_id_of_object (void *ptr) {
123
+ //
124
+ // We don't have to deal with the "1 past the end of block" case because
125
+ // a valid pointer will always point into our hyperblock - we will never return
126
+ // an allocation anywhere near the end of our hyperblock.
127
+ //
128
+ // Set the low bits to 1 to get the address of the last byte in the hyperblock.
129
+ //
130
+ uintptr_t end_address
131
+ = reinterpret_cast <uintptr_t >(ptr) | (HYPERBLOCK_SIZE - 1 );
132
+ return *reinterpret_cast <char *>(end_address);
133
+ }
134
+
149
135
// Macro to define a new arena with the given ID. Supports IDs ranging from 0 to
150
136
// 127.
151
- #define REGISTER_ARENA (name, id ) static thread_local arena name (id)
137
+ #define REGISTER_ARENA (name, id ) thread_local arena name (id)
152
138
153
139
#ifdef __MACH__
154
140
//
@@ -169,8 +155,11 @@ inline void *arena::kore_arena_alloc(size_t requested) {
169
155
// collect when allowed.
170
156
//
171
157
time_for_collection = true ;
172
- tripwire = current_addr_ptr
173
- + HYPERBLOCK_SIZE; // won't trigger again until arena swap
158
+ //
159
+ // We move the tripwire to 1 past the end of our hyperblock so that we have
160
+ // a well defined comparison that will always be false until the next arena swap.
161
+ //
162
+ tripwire = current_addr_ptr + HYPERBLOCK_SIZE;
174
163
}
175
164
void *result = allocation_ptr;
176
165
allocation_ptr += requested;
0 commit comments