blob: 424f2f340eff02bfa731f04b7dac94e19680121c [file] [log] [blame]
Mathieu Chartierb43b7d42012-06-19 13:15:09 -07001/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef ART_SRC_MOD_UNION_TABLE_H_
18#define ART_SRC_MOD_UNION_TABLE_H_
19
Mathieu Chartiercc236d72012-07-20 10:29:05 -070020#include "heap.h"
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070021#include "safe_map.h"
Mathieu Chartiercc236d72012-07-20 10:29:05 -070022#include "space.h"
23
24#define VERIFY_MOD_UNION 0
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070025
26namespace art {
27
28class Heap;
29class HeapBitmap;
30class Space;
31
Mathieu Chartiercc236d72012-07-20 10:29:05 -070032// Base class
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070033class ModUnionTable {
34 public:
Mathieu Chartiercc236d72012-07-20 10:29:05 -070035 typedef std::vector<const Object*> ReferenceArray;
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070036
Mathieu Chartiercc236d72012-07-20 10:29:05 -070037 ModUnionTable(Heap* heap) : heap_(heap), mark_sweep_(0) {
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070038
Mathieu Chartiercc236d72012-07-20 10:29:05 -070039 }
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070040
41 virtual ~ModUnionTable() {
42
43 }
Mathieu Chartiercc236d72012-07-20 10:29:05 -070044
45 // Clear cards which map to a memory range of a space.
46 virtual void ClearCards(Space* space) = 0;
47
48 // Update the mod-union table.
49 virtual void Update() = 0;
50
51 // Mark all references which are stored in the mod union table.
52 virtual void MarkReferences() = 0;
53
54 // Verification, sanity checks that we don't have clean cards which conflict with out cached data
55 // for said cards.
56 virtual void Verify() = 0;
57
58 // Should probably clean this up later.
59 void Init(MarkSweep* mark_sweep) {
60 mark_sweep_ = mark_sweep;
61 }
62
63 MarkSweep* GetMarkSweep() {
64 return mark_sweep_;
65 }
66
67 Heap* GetHeap() {
68 return heap_;
69 }
70
71 protected:
72 Heap* heap_;
73 MarkSweep* mark_sweep_;
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070074};
75
76// Bitmap implementation.
Mathieu Chartiercc236d72012-07-20 10:29:05 -070077// DEPRECATED, performs strictly less well than merely caching which cards were dirty.
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070078class ModUnionTableBitmap : public ModUnionTable {
79 public:
80 ModUnionTableBitmap(Heap* heap);
81 virtual ~ModUnionTableBitmap();
82
Mathieu Chartiercc236d72012-07-20 10:29:05 -070083 // Clear space cards.
84 void ClearCards(Space* space);
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070085
86 // Update table based on cleared cards.
Ian Rogers00f7d0e2012-07-19 15:28:27 -070087 void Update()
88 EXCLUSIVE_LOCKS_REQUIRED(GlobalSynchronization::heap_bitmap_lock_)
89 SHARED_LOCKS_REQUIRED(GlobalSynchronization::mutator_lock_);
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070090
91 // Mark all references to the alloc space(s).
Ian Rogers00f7d0e2012-07-19 15:28:27 -070092 void MarkReferences() EXCLUSIVE_LOCKS_REQUIRED(GlobalSynchronization::heap_bitmap_lock_);
Mathieu Chartiercc236d72012-07-20 10:29:05 -070093
94 protected:
Mathieu Chartierb43b7d42012-06-19 13:15:09 -070095 // Cleared card array, used to update the mod-union table.
96 std::vector<byte*> cleared_cards_;
97
98 // One bitmap per image space.
Mathieu Chartiercc236d72012-07-20 10:29:05 -070099 // TODO: Add support for Zygote spaces?
100 typedef SafeMap<Space*, SpaceBitmap*> BitmapMap;
Mathieu Chartierb43b7d42012-06-19 13:15:09 -0700101 BitmapMap bitmaps_;
Mathieu Chartierb43b7d42012-06-19 13:15:09 -0700102};
103
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700104// Reference caching implementation. Caches references pointing to alloc space(s) for each card.
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700105class ModUnionTableReferenceCache : public ModUnionTable {
106 public:
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700107 typedef SafeMap<const byte*, ReferenceArray > ReferenceMap;
108
109 ModUnionTableReferenceCache(Heap* heap);
110 virtual ~ModUnionTableReferenceCache();
111
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700112 // Clear and store cards for a space.
113 void ClearCards(Space* space);
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700114
115 // Update table based on cleared cards.
Ian Rogers00f7d0e2012-07-19 15:28:27 -0700116 void Update()
117 EXCLUSIVE_LOCKS_REQUIRED(GlobalSynchronization::heap_bitmap_lock_)
118 SHARED_LOCKS_REQUIRED(GlobalSynchronization::mutator_lock_);
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700119
120 // Mark all references to the alloc space(s).
Ian Rogers00f7d0e2012-07-19 15:28:27 -0700121 void MarkReferences() EXCLUSIVE_LOCKS_REQUIRED(GlobalSynchronization::heap_bitmap_lock_);
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700122
123 // Verify the mod-union table.
124 void Verify();
125
126 // Function that tells whether or not to add a reference to the table.
127 virtual bool AddReference(const Object* obj, const Object* ref) = 0;
128
129 protected:
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700130 // Cleared card array, used to update the mod-union table.
131 std::vector<byte*> cleared_cards_;
132
133 // Maps from dirty cards to their corresponding alloc space references.
134 ReferenceMap references_;
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700135};
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700136
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700137// Card caching implementation. Keeps track of which cards we cleared and only this information.
138class ModUnionTableCardCache : public ModUnionTable {
139 public:
140 typedef std::set<byte*> ClearedCards;
141 typedef SafeMap<const byte*, ReferenceArray > ReferenceMap;
142
143 ModUnionTableCardCache(Heap* heap);
144 virtual ~ModUnionTableCardCache();
145
146 // Clear and store cards for a space.
147 void ClearCards(Space* space);
148
149 // Nothing to update.
150 void Update() {}
151
152 // Mark all references to the alloc space(s).
Ian Rogers00f7d0e2012-07-19 15:28:27 -0700153 void MarkReferences()
154 EXCLUSIVE_LOCKS_REQUIRED(GlobalSynchronization::heap_bitmap_lock_)
155 SHARED_LOCKS_REQUIRED(GlobalSynchronization::mutator_lock_);
Mathieu Chartiercc236d72012-07-20 10:29:05 -0700156
157 // Nothing to verify.
158 void Verify() {}
159
160 protected:
161 // Cleared card array, used to update the mod-union table.
162 ClearedCards cleared_cards_;
163};
164
165template <typename Implementation>
166class ModUnionTableToZygoteAllocspace : public Implementation {
167public:
168 ModUnionTableToZygoteAllocspace(Heap* heap) : Implementation(heap) {
169 }
170
171 bool AddReference(const Object* /* obj */, const Object* ref) {
172 const Spaces& spaces = Implementation::GetMarkSweep()->GetHeap()->GetSpaces();
173 for (Spaces::const_iterator it = spaces.begin(); it != spaces.end(); ++it) {
174 if ((*it)->Contains(ref)) {
175 return (*it)->IsAllocSpace();
176 }
177 }
178 if (ref != NULL) {
179 Implementation::GetHeap()->DumpSpaces();
180 LOG(FATAL) << "Reference " << ref << " not in any space!";
181 }
182 return false;
183 }
184};
185
186template <typename Implementation>
187class ModUnionTableToAllocspace : public Implementation {
188public:
189 ModUnionTableToAllocspace(Heap* heap) : Implementation(heap) {
190 }
191
192 bool AddReference(const Object* /* obj */, const Object* ref) {
193 const Spaces& spaces = Implementation::GetMarkSweep()->GetHeap()->GetSpaces();
194 for (Spaces::const_iterator it = spaces.begin(); it != spaces.end(); ++it) {
195 if ((*it)->Contains(ref)) {
196 return (*it)->GetGcRetentionPolicy() == GCRP_ALWAYS_COLLECT;
197 }
198 }
199 if (ref != NULL) {
200 Implementation::GetHeap()->DumpSpaces();
201 LOG(FATAL) << "Reference " << ref << " not in any space!";
202 }
203 return false;
204 }
Mathieu Chartiere6e06512012-06-26 15:00:26 -0700205};
206
Mathieu Chartierb43b7d42012-06-19 13:15:09 -0700207} // namespace art
208
209#endif // ART_SRC_MOD_UNION_TABLE_H_