annotate src/share/vm/gc_implementation/parallelScavenge/cardTableExtension.cpp @ 6862:8a5ea0a9ccc4

7127708: G1: change task num types from int to uint in concurrent mark Summary: Change the type of various task num fields, parameters etc to unsigned and rename them to be more consistent with the other collectors. Code changes were also reviewed by Vitaly Davidovich. Reviewed-by: johnc Contributed-by: Kaushik Srenevasan <kaushik@twitter.com>
author johnc
date Sat, 06 Oct 2012 01:17:44 -0700
parents f81a7c0c618d
children 746b070f5022
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
6725
da91efe96a93 6964458: Reimplement class meta-data storage to use native memory
coleenp
parents: 6009
diff changeset
2 * Copyright (c) 2001, 2012, Oracle and/or its affiliates. All rights reserved.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
a61af66fc99e Initial load
duke
parents:
diff changeset
4 *
a61af66fc99e Initial load
duke
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
a61af66fc99e Initial load
duke
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
a61af66fc99e Initial load
duke
parents:
diff changeset
7 * published by the Free Software Foundation.
a61af66fc99e Initial load
duke
parents:
diff changeset
8 *
a61af66fc99e Initial load
duke
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
a61af66fc99e Initial load
duke
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a61af66fc99e Initial load
duke
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a61af66fc99e Initial load
duke
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
a61af66fc99e Initial load
duke
parents:
diff changeset
13 * accompanied this code).
a61af66fc99e Initial load
duke
parents:
diff changeset
14 *
a61af66fc99e Initial load
duke
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
a61af66fc99e Initial load
duke
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
a61af66fc99e Initial load
duke
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
a61af66fc99e Initial load
duke
parents:
diff changeset
18 *
1552
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
20 * or visit www.oracle.com if you need additional information or have any
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 605
diff changeset
21 * questions.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
22 *
a61af66fc99e Initial load
duke
parents:
diff changeset
23 */
a61af66fc99e Initial load
duke
parents:
diff changeset
24
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
25 #include "precompiled.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
26 #include "gc_implementation/parallelScavenge/cardTableExtension.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
27 #include "gc_implementation/parallelScavenge/gcTaskManager.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
28 #include "gc_implementation/parallelScavenge/parallelScavengeHeap.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
29 #include "gc_implementation/parallelScavenge/psTasks.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
30 #include "gc_implementation/parallelScavenge/psYoungGen.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
31 #include "oops/oop.inline.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1706
diff changeset
32 #include "oops/oop.psgc.inline.hpp"
0
a61af66fc99e Initial load
duke
parents:
diff changeset
33
a61af66fc99e Initial load
duke
parents:
diff changeset
34 // Checks an individual oop for missing precise marks. Mark
a61af66fc99e Initial load
duke
parents:
diff changeset
35 // may be either dirty or newgen.
a61af66fc99e Initial load
duke
parents:
diff changeset
36 class CheckForUnmarkedOops : public OopClosure {
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
37 private:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
38 PSYoungGen* _young_gen;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
39 CardTableExtension* _card_table;
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
40 HeapWord* _unmarked_addr;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
41 jbyte* _unmarked_card;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
42
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
43 protected:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
44 template <class T> void do_oop_work(T* p) {
6009
dde53abda3d6 7160613: VerifyRememberedSets doesn't work with CompressedOops
stefank
parents: 4095
diff changeset
45 oop obj = oopDesc::load_decode_heap_oop(p);
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
46 if (_young_gen->is_in_reserved(obj) &&
0
a61af66fc99e Initial load
duke
parents:
diff changeset
47 !_card_table->addr_is_marked_imprecise(p)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
48 // Don't overwrite the first missing card mark
a61af66fc99e Initial load
duke
parents:
diff changeset
49 if (_unmarked_addr == NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
50 _unmarked_addr = (HeapWord*)p;
a61af66fc99e Initial load
duke
parents:
diff changeset
51 _unmarked_card = _card_table->byte_for(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
52 }
a61af66fc99e Initial load
duke
parents:
diff changeset
53 }
a61af66fc99e Initial load
duke
parents:
diff changeset
54 }
a61af66fc99e Initial load
duke
parents:
diff changeset
55
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
56 public:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
57 CheckForUnmarkedOops(PSYoungGen* young_gen, CardTableExtension* card_table) :
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
58 _young_gen(young_gen), _card_table(card_table), _unmarked_addr(NULL) { }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
59
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
60 virtual void do_oop(oop* p) { CheckForUnmarkedOops::do_oop_work(p); }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
61 virtual void do_oop(narrowOop* p) { CheckForUnmarkedOops::do_oop_work(p); }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
62
0
a61af66fc99e Initial load
duke
parents:
diff changeset
63 bool has_unmarked_oop() {
a61af66fc99e Initial load
duke
parents:
diff changeset
64 return _unmarked_addr != NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
65 }
a61af66fc99e Initial load
duke
parents:
diff changeset
66 };
a61af66fc99e Initial load
duke
parents:
diff changeset
67
a61af66fc99e Initial load
duke
parents:
diff changeset
68 // Checks all objects for the existance of some type of mark,
a61af66fc99e Initial load
duke
parents:
diff changeset
69 // precise or imprecise, dirty or newgen.
a61af66fc99e Initial load
duke
parents:
diff changeset
70 class CheckForUnmarkedObjects : public ObjectClosure {
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
71 private:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
72 PSYoungGen* _young_gen;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
73 CardTableExtension* _card_table;
a61af66fc99e Initial load
duke
parents:
diff changeset
74
a61af66fc99e Initial load
duke
parents:
diff changeset
75 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
76 CheckForUnmarkedObjects() {
a61af66fc99e Initial load
duke
parents:
diff changeset
77 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
78 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity");
a61af66fc99e Initial load
duke
parents:
diff changeset
79
a61af66fc99e Initial load
duke
parents:
diff changeset
80 _young_gen = heap->young_gen();
a61af66fc99e Initial load
duke
parents:
diff changeset
81 _card_table = (CardTableExtension*)heap->barrier_set();
a61af66fc99e Initial load
duke
parents:
diff changeset
82 // No point in asserting barrier set type here. Need to make CardTableExtension
a61af66fc99e Initial load
duke
parents:
diff changeset
83 // a unique barrier set type.
a61af66fc99e Initial load
duke
parents:
diff changeset
84 }
a61af66fc99e Initial load
duke
parents:
diff changeset
85
a61af66fc99e Initial load
duke
parents:
diff changeset
86 // Card marks are not precise. The current system can leave us with
605
98cb887364d3 6810672: Comment typos
twisti
parents: 269
diff changeset
87 // a mismash of precise marks and beginning of object marks. This means
0
a61af66fc99e Initial load
duke
parents:
diff changeset
88 // we test for missing precise marks first. If any are found, we don't
a61af66fc99e Initial load
duke
parents:
diff changeset
89 // fail unless the object head is also unmarked.
a61af66fc99e Initial load
duke
parents:
diff changeset
90 virtual void do_object(oop obj) {
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
91 CheckForUnmarkedOops object_check(_young_gen, _card_table);
6725
da91efe96a93 6964458: Reimplement class meta-data storage to use native memory
coleenp
parents: 6009
diff changeset
92 obj->oop_iterate_no_header(&object_check);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
93 if (object_check.has_unmarked_oop()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
94 assert(_card_table->addr_is_marked_imprecise(obj), "Found unmarked young_gen object");
a61af66fc99e Initial load
duke
parents:
diff changeset
95 }
a61af66fc99e Initial load
duke
parents:
diff changeset
96 }
a61af66fc99e Initial load
duke
parents:
diff changeset
97 };
a61af66fc99e Initial load
duke
parents:
diff changeset
98
a61af66fc99e Initial load
duke
parents:
diff changeset
99 // Checks for precise marking of oops as newgen.
a61af66fc99e Initial load
duke
parents:
diff changeset
100 class CheckForPreciseMarks : public OopClosure {
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
101 private:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
102 PSYoungGen* _young_gen;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
103 CardTableExtension* _card_table;
a61af66fc99e Initial load
duke
parents:
diff changeset
104
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
105 protected:
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
106 template <class T> void do_oop_work(T* p) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
107 oop obj = oopDesc::load_decode_heap_oop_not_null(p);
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
108 if (_young_gen->is_in_reserved(obj)) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
109 assert(_card_table->addr_is_marked_precise(p), "Found unmarked precise oop");
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
110 _card_table->set_card_newgen(p);
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
111 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
112 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
113
0
a61af66fc99e Initial load
duke
parents:
diff changeset
114 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
115 CheckForPreciseMarks( PSYoungGen* young_gen, CardTableExtension* card_table ) :
a61af66fc99e Initial load
duke
parents:
diff changeset
116 _young_gen(young_gen), _card_table(card_table) { }
a61af66fc99e Initial load
duke
parents:
diff changeset
117
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
118 virtual void do_oop(oop* p) { CheckForPreciseMarks::do_oop_work(p); }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
119 virtual void do_oop(narrowOop* p) { CheckForPreciseMarks::do_oop_work(p); }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
120 };
a61af66fc99e Initial load
duke
parents:
diff changeset
121
a61af66fc99e Initial load
duke
parents:
diff changeset
122 // We get passed the space_top value to prevent us from traversing into
a61af66fc99e Initial load
duke
parents:
diff changeset
123 // the old_gen promotion labs, which cannot be safely parsed.
a61af66fc99e Initial load
duke
parents:
diff changeset
124
6817
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
125 // Do not call this method if the space is empty.
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
126 // It is a waste to start tasks and get here only to
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
127 // do no work. If this method needs to be called
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
128 // when the space is empty, fix the calculation of
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
129 // end_card to allow sp_top == sp->bottom().
0
a61af66fc99e Initial load
duke
parents:
diff changeset
130
a61af66fc99e Initial load
duke
parents:
diff changeset
131 void CardTableExtension::scavenge_contents_parallel(ObjectStartArray* start_array,
a61af66fc99e Initial load
duke
parents:
diff changeset
132 MutableSpace* sp,
a61af66fc99e Initial load
duke
parents:
diff changeset
133 HeapWord* space_top,
a61af66fc99e Initial load
duke
parents:
diff changeset
134 PSPromotionManager* pm,
4095
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
135 uint stripe_number,
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
136 uint stripe_total) {
0
a61af66fc99e Initial load
duke
parents:
diff changeset
137 int ssize = 128; // Naked constant! Work unit = 64k.
a61af66fc99e Initial load
duke
parents:
diff changeset
138 int dirty_card_count = 0;
a61af66fc99e Initial load
duke
parents:
diff changeset
139
6817
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
140 // It is a waste to get here if empty.
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
141 assert(sp->bottom() < sp->top(), "Should not be called if empty");
0
a61af66fc99e Initial load
duke
parents:
diff changeset
142 oop* sp_top = (oop*)space_top;
a61af66fc99e Initial load
duke
parents:
diff changeset
143 jbyte* start_card = byte_for(sp->bottom());
6817
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
144 jbyte* end_card = byte_for(sp_top - 1) + 1;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
145 oop* last_scanned = NULL; // Prevent scanning objects more than once
4095
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
146 // The width of the stripe ssize*stripe_total must be
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
147 // consistent with the number of stripes so that the complete slice
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
148 // is covered.
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
149 size_t slice_width = ssize * stripe_total;
bca17e38de00 6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents: 1972
diff changeset
150 for (jbyte* slice = start_card; slice < end_card; slice += slice_width) {
0
a61af66fc99e Initial load
duke
parents:
diff changeset
151 jbyte* worker_start_card = slice + stripe_number * ssize;
a61af66fc99e Initial load
duke
parents:
diff changeset
152 if (worker_start_card >= end_card)
a61af66fc99e Initial load
duke
parents:
diff changeset
153 return; // We're done.
a61af66fc99e Initial load
duke
parents:
diff changeset
154
a61af66fc99e Initial load
duke
parents:
diff changeset
155 jbyte* worker_end_card = worker_start_card + ssize;
a61af66fc99e Initial load
duke
parents:
diff changeset
156 if (worker_end_card > end_card)
a61af66fc99e Initial load
duke
parents:
diff changeset
157 worker_end_card = end_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
158
a61af66fc99e Initial load
duke
parents:
diff changeset
159 // We do not want to scan objects more than once. In order to accomplish
a61af66fc99e Initial load
duke
parents:
diff changeset
160 // this, we assert that any object with an object head inside our 'slice'
a61af66fc99e Initial load
duke
parents:
diff changeset
161 // belongs to us. We may need to extend the range of scanned cards if the
a61af66fc99e Initial load
duke
parents:
diff changeset
162 // last object continues into the next 'slice'.
a61af66fc99e Initial load
duke
parents:
diff changeset
163 //
a61af66fc99e Initial load
duke
parents:
diff changeset
164 // Note! ending cards are exclusive!
a61af66fc99e Initial load
duke
parents:
diff changeset
165 HeapWord* slice_start = addr_for(worker_start_card);
a61af66fc99e Initial load
duke
parents:
diff changeset
166 HeapWord* slice_end = MIN2((HeapWord*) sp_top, addr_for(worker_end_card));
a61af66fc99e Initial load
duke
parents:
diff changeset
167
6817
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
168 #ifdef ASSERT
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
169 if (GCWorkerDelayMillis > 0) {
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
170 // Delay 1 worker so that it proceeds after all the work
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
171 // has been completed.
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
172 if (stripe_number < 2) {
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
173 os::sleep(Thread::current(), GCWorkerDelayMillis, false);
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
174 }
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
175 }
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
176 #endif
f81a7c0c618d 7199349: NPG: PS: Crash seen in jprt
jmasa
parents: 6725
diff changeset
177
0
a61af66fc99e Initial load
duke
parents:
diff changeset
178 // If there are not objects starting within the chunk, skip it.
a61af66fc99e Initial load
duke
parents:
diff changeset
179 if (!start_array->object_starts_in_range(slice_start, slice_end)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
180 continue;
a61af66fc99e Initial load
duke
parents:
diff changeset
181 }
605
98cb887364d3 6810672: Comment typos
twisti
parents: 269
diff changeset
182 // Update our beginning addr
0
a61af66fc99e Initial load
duke
parents:
diff changeset
183 HeapWord* first_object = start_array->object_start(slice_start);
a61af66fc99e Initial load
duke
parents:
diff changeset
184 debug_only(oop* first_object_within_slice = (oop*) first_object;)
a61af66fc99e Initial load
duke
parents:
diff changeset
185 if (first_object < slice_start) {
a61af66fc99e Initial load
duke
parents:
diff changeset
186 last_scanned = (oop*)(first_object + oop(first_object)->size());
a61af66fc99e Initial load
duke
parents:
diff changeset
187 debug_only(first_object_within_slice = last_scanned;)
a61af66fc99e Initial load
duke
parents:
diff changeset
188 worker_start_card = byte_for(last_scanned);
a61af66fc99e Initial load
duke
parents:
diff changeset
189 }
a61af66fc99e Initial load
duke
parents:
diff changeset
190
a61af66fc99e Initial load
duke
parents:
diff changeset
191 // Update the ending addr
a61af66fc99e Initial load
duke
parents:
diff changeset
192 if (slice_end < (HeapWord*)sp_top) {
a61af66fc99e Initial load
duke
parents:
diff changeset
193 // The subtraction is important! An object may start precisely at slice_end.
a61af66fc99e Initial load
duke
parents:
diff changeset
194 HeapWord* last_object = start_array->object_start(slice_end - 1);
a61af66fc99e Initial load
duke
parents:
diff changeset
195 slice_end = last_object + oop(last_object)->size();
a61af66fc99e Initial load
duke
parents:
diff changeset
196 // worker_end_card is exclusive, so bump it one past the end of last_object's
a61af66fc99e Initial load
duke
parents:
diff changeset
197 // covered span.
a61af66fc99e Initial load
duke
parents:
diff changeset
198 worker_end_card = byte_for(slice_end) + 1;
a61af66fc99e Initial load
duke
parents:
diff changeset
199
a61af66fc99e Initial load
duke
parents:
diff changeset
200 if (worker_end_card > end_card)
a61af66fc99e Initial load
duke
parents:
diff changeset
201 worker_end_card = end_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
202 }
a61af66fc99e Initial load
duke
parents:
diff changeset
203
a61af66fc99e Initial load
duke
parents:
diff changeset
204 assert(slice_end <= (HeapWord*)sp_top, "Last object in slice crosses space boundary");
a61af66fc99e Initial load
duke
parents:
diff changeset
205 assert(is_valid_card_address(worker_start_card), "Invalid worker start card");
a61af66fc99e Initial load
duke
parents:
diff changeset
206 assert(is_valid_card_address(worker_end_card), "Invalid worker end card");
a61af66fc99e Initial load
duke
parents:
diff changeset
207 // Note that worker_start_card >= worker_end_card is legal, and happens when
a61af66fc99e Initial load
duke
parents:
diff changeset
208 // an object spans an entire slice.
a61af66fc99e Initial load
duke
parents:
diff changeset
209 assert(worker_start_card <= end_card, "worker start card beyond end card");
a61af66fc99e Initial load
duke
parents:
diff changeset
210 assert(worker_end_card <= end_card, "worker end card beyond end card");
a61af66fc99e Initial load
duke
parents:
diff changeset
211
a61af66fc99e Initial load
duke
parents:
diff changeset
212 jbyte* current_card = worker_start_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
213 while (current_card < worker_end_card) {
a61af66fc99e Initial load
duke
parents:
diff changeset
214 // Find an unclean card.
a61af66fc99e Initial load
duke
parents:
diff changeset
215 while (current_card < worker_end_card && card_is_clean(*current_card)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
216 current_card++;
a61af66fc99e Initial load
duke
parents:
diff changeset
217 }
a61af66fc99e Initial load
duke
parents:
diff changeset
218 jbyte* first_unclean_card = current_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
219
a61af66fc99e Initial load
duke
parents:
diff changeset
220 // Find the end of a run of contiguous unclean cards
a61af66fc99e Initial load
duke
parents:
diff changeset
221 while (current_card < worker_end_card && !card_is_clean(*current_card)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
222 while (current_card < worker_end_card && !card_is_clean(*current_card)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
223 current_card++;
a61af66fc99e Initial load
duke
parents:
diff changeset
224 }
a61af66fc99e Initial load
duke
parents:
diff changeset
225
a61af66fc99e Initial load
duke
parents:
diff changeset
226 if (current_card < worker_end_card) {
a61af66fc99e Initial load
duke
parents:
diff changeset
227 // Some objects may be large enough to span several cards. If such
a61af66fc99e Initial load
duke
parents:
diff changeset
228 // an object has more than one dirty card, separated by a clean card,
a61af66fc99e Initial load
duke
parents:
diff changeset
229 // we will attempt to scan it twice. The test against "last_scanned"
a61af66fc99e Initial load
duke
parents:
diff changeset
230 // prevents the redundant object scan, but it does not prevent newly
a61af66fc99e Initial load
duke
parents:
diff changeset
231 // marked cards from being cleaned.
a61af66fc99e Initial load
duke
parents:
diff changeset
232 HeapWord* last_object_in_dirty_region = start_array->object_start(addr_for(current_card)-1);
a61af66fc99e Initial load
duke
parents:
diff changeset
233 size_t size_of_last_object = oop(last_object_in_dirty_region)->size();
a61af66fc99e Initial load
duke
parents:
diff changeset
234 HeapWord* end_of_last_object = last_object_in_dirty_region + size_of_last_object;
a61af66fc99e Initial load
duke
parents:
diff changeset
235 jbyte* ending_card_of_last_object = byte_for(end_of_last_object);
a61af66fc99e Initial load
duke
parents:
diff changeset
236 assert(ending_card_of_last_object <= worker_end_card, "ending_card_of_last_object is greater than worker_end_card");
a61af66fc99e Initial load
duke
parents:
diff changeset
237 if (ending_card_of_last_object > current_card) {
a61af66fc99e Initial load
duke
parents:
diff changeset
238 // This means the object spans the next complete card.
a61af66fc99e Initial load
duke
parents:
diff changeset
239 // We need to bump the current_card to ending_card_of_last_object
a61af66fc99e Initial load
duke
parents:
diff changeset
240 current_card = ending_card_of_last_object;
a61af66fc99e Initial load
duke
parents:
diff changeset
241 }
a61af66fc99e Initial load
duke
parents:
diff changeset
242 }
a61af66fc99e Initial load
duke
parents:
diff changeset
243 }
a61af66fc99e Initial load
duke
parents:
diff changeset
244 jbyte* following_clean_card = current_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
245
a61af66fc99e Initial load
duke
parents:
diff changeset
246 if (first_unclean_card < worker_end_card) {
a61af66fc99e Initial load
duke
parents:
diff changeset
247 oop* p = (oop*) start_array->object_start(addr_for(first_unclean_card));
a61af66fc99e Initial load
duke
parents:
diff changeset
248 assert((HeapWord*)p <= addr_for(first_unclean_card), "checking");
a61af66fc99e Initial load
duke
parents:
diff changeset
249 // "p" should always be >= "last_scanned" because newly GC dirtied
a61af66fc99e Initial load
duke
parents:
diff changeset
250 // cards are no longer scanned again (see comment at end
a61af66fc99e Initial load
duke
parents:
diff changeset
251 // of loop on the increment of "current_card"). Test that
a61af66fc99e Initial load
duke
parents:
diff changeset
252 // hypothesis before removing this code.
a61af66fc99e Initial load
duke
parents:
diff changeset
253 // If this code is removed, deal with the first time through
a61af66fc99e Initial load
duke
parents:
diff changeset
254 // the loop when the last_scanned is the object starting in
a61af66fc99e Initial load
duke
parents:
diff changeset
255 // the previous slice.
a61af66fc99e Initial load
duke
parents:
diff changeset
256 assert((p >= last_scanned) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
257 (last_scanned == first_object_within_slice),
a61af66fc99e Initial load
duke
parents:
diff changeset
258 "Should no longer be possible");
a61af66fc99e Initial load
duke
parents:
diff changeset
259 if (p < last_scanned) {
a61af66fc99e Initial load
duke
parents:
diff changeset
260 // Avoid scanning more than once; this can happen because
a61af66fc99e Initial load
duke
parents:
diff changeset
261 // newgen cards set by GC may a different set than the
a61af66fc99e Initial load
duke
parents:
diff changeset
262 // originally dirty set
a61af66fc99e Initial load
duke
parents:
diff changeset
263 p = last_scanned;
a61af66fc99e Initial load
duke
parents:
diff changeset
264 }
a61af66fc99e Initial load
duke
parents:
diff changeset
265 oop* to = (oop*)addr_for(following_clean_card);
a61af66fc99e Initial load
duke
parents:
diff changeset
266
a61af66fc99e Initial load
duke
parents:
diff changeset
267 // Test slice_end first!
a61af66fc99e Initial load
duke
parents:
diff changeset
268 if ((HeapWord*)to > slice_end) {
a61af66fc99e Initial load
duke
parents:
diff changeset
269 to = (oop*)slice_end;
a61af66fc99e Initial load
duke
parents:
diff changeset
270 } else if (to > sp_top) {
a61af66fc99e Initial load
duke
parents:
diff changeset
271 to = sp_top;
a61af66fc99e Initial load
duke
parents:
diff changeset
272 }
a61af66fc99e Initial load
duke
parents:
diff changeset
273
a61af66fc99e Initial load
duke
parents:
diff changeset
274 // we know which cards to scan, now clear them
a61af66fc99e Initial load
duke
parents:
diff changeset
275 if (first_unclean_card <= worker_start_card+1)
a61af66fc99e Initial load
duke
parents:
diff changeset
276 first_unclean_card = worker_start_card+1;
a61af66fc99e Initial load
duke
parents:
diff changeset
277 if (following_clean_card >= worker_end_card-1)
a61af66fc99e Initial load
duke
parents:
diff changeset
278 following_clean_card = worker_end_card-1;
a61af66fc99e Initial load
duke
parents:
diff changeset
279
a61af66fc99e Initial load
duke
parents:
diff changeset
280 while (first_unclean_card < following_clean_card) {
a61af66fc99e Initial load
duke
parents:
diff changeset
281 *first_unclean_card++ = clean_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
282 }
a61af66fc99e Initial load
duke
parents:
diff changeset
283
a61af66fc99e Initial load
duke
parents:
diff changeset
284 const int interval = PrefetchScanIntervalInBytes;
a61af66fc99e Initial load
duke
parents:
diff changeset
285 // scan all objects in the range
a61af66fc99e Initial load
duke
parents:
diff changeset
286 if (interval != 0) {
1706
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
287 while (p < to) {
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
288 Prefetch::write(p, interval);
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
289 oop m = oop(p);
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
290 assert(m->is_oop_or_null(), "check for header");
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
291 m->push_contents(pm);
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
292 p += m->size();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
293 }
1706
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
294 pm->drain_stacks_cond_depth();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
295 } else {
1706
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
296 while (p < to) {
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
297 oop m = oop(p);
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
298 assert(m->is_oop_or_null(), "check for header");
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
299 m->push_contents(pm);
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
300 p += m->size();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
301 }
1706
9d7a8ab3736b 6962589: remove breadth first scanning code from parallel gc
tonyp
parents: 1612
diff changeset
302 pm->drain_stacks_cond_depth();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
303 }
a61af66fc99e Initial load
duke
parents:
diff changeset
304 last_scanned = p;
a61af66fc99e Initial load
duke
parents:
diff changeset
305 }
a61af66fc99e Initial load
duke
parents:
diff changeset
306 // "current_card" is still the "following_clean_card" or
a61af66fc99e Initial load
duke
parents:
diff changeset
307 // the current_card is >= the worker_end_card so the
a61af66fc99e Initial load
duke
parents:
diff changeset
308 // loop will not execute again.
a61af66fc99e Initial load
duke
parents:
diff changeset
309 assert((current_card == following_clean_card) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
310 (current_card >= worker_end_card),
a61af66fc99e Initial load
duke
parents:
diff changeset
311 "current_card should only be incremented if it still equals "
a61af66fc99e Initial load
duke
parents:
diff changeset
312 "following_clean_card");
a61af66fc99e Initial load
duke
parents:
diff changeset
313 // Increment current_card so that it is not processed again.
a61af66fc99e Initial load
duke
parents:
diff changeset
314 // It may now be dirty because a old-to-young pointer was
a61af66fc99e Initial load
duke
parents:
diff changeset
315 // found on it an updated. If it is now dirty, it cannot be
a61af66fc99e Initial load
duke
parents:
diff changeset
316 // be safely cleaned in the next iteration.
a61af66fc99e Initial load
duke
parents:
diff changeset
317 current_card++;
a61af66fc99e Initial load
duke
parents:
diff changeset
318 }
a61af66fc99e Initial load
duke
parents:
diff changeset
319 }
a61af66fc99e Initial load
duke
parents:
diff changeset
320 }
a61af66fc99e Initial load
duke
parents:
diff changeset
321
a61af66fc99e Initial load
duke
parents:
diff changeset
322 // This should be called before a scavenge.
a61af66fc99e Initial load
duke
parents:
diff changeset
323 void CardTableExtension::verify_all_young_refs_imprecise() {
a61af66fc99e Initial load
duke
parents:
diff changeset
324 CheckForUnmarkedObjects check;
a61af66fc99e Initial load
duke
parents:
diff changeset
325
a61af66fc99e Initial load
duke
parents:
diff changeset
326 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
327 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity");
a61af66fc99e Initial load
duke
parents:
diff changeset
328
a61af66fc99e Initial load
duke
parents:
diff changeset
329 PSOldGen* old_gen = heap->old_gen();
a61af66fc99e Initial load
duke
parents:
diff changeset
330
a61af66fc99e Initial load
duke
parents:
diff changeset
331 old_gen->object_iterate(&check);
a61af66fc99e Initial load
duke
parents:
diff changeset
332 }
a61af66fc99e Initial load
duke
parents:
diff changeset
333
a61af66fc99e Initial load
duke
parents:
diff changeset
334 // This should be called immediately after a scavenge, before mutators resume.
a61af66fc99e Initial load
duke
parents:
diff changeset
335 void CardTableExtension::verify_all_young_refs_precise() {
a61af66fc99e Initial load
duke
parents:
diff changeset
336 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
337 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity");
a61af66fc99e Initial load
duke
parents:
diff changeset
338
a61af66fc99e Initial load
duke
parents:
diff changeset
339 PSOldGen* old_gen = heap->old_gen();
a61af66fc99e Initial load
duke
parents:
diff changeset
340
a61af66fc99e Initial load
duke
parents:
diff changeset
341 CheckForPreciseMarks check(heap->young_gen(), (CardTableExtension*)heap->barrier_set());
a61af66fc99e Initial load
duke
parents:
diff changeset
342
6725
da91efe96a93 6964458: Reimplement class meta-data storage to use native memory
coleenp
parents: 6009
diff changeset
343 old_gen->oop_iterate_no_header(&check);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
344
a61af66fc99e Initial load
duke
parents:
diff changeset
345 verify_all_young_refs_precise_helper(old_gen->object_space()->used_region());
a61af66fc99e Initial load
duke
parents:
diff changeset
346 }
a61af66fc99e Initial load
duke
parents:
diff changeset
347
a61af66fc99e Initial load
duke
parents:
diff changeset
348 void CardTableExtension::verify_all_young_refs_precise_helper(MemRegion mr) {
a61af66fc99e Initial load
duke
parents:
diff changeset
349 CardTableExtension* card_table = (CardTableExtension*)Universe::heap()->barrier_set();
a61af66fc99e Initial load
duke
parents:
diff changeset
350 // FIX ME ASSERT HERE
a61af66fc99e Initial load
duke
parents:
diff changeset
351
a61af66fc99e Initial load
duke
parents:
diff changeset
352 jbyte* bot = card_table->byte_for(mr.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
353 jbyte* top = card_table->byte_for(mr.end());
a61af66fc99e Initial load
duke
parents:
diff changeset
354 while(bot <= top) {
a61af66fc99e Initial load
duke
parents:
diff changeset
355 assert(*bot == clean_card || *bot == verify_card, "Found unwanted or unknown card mark");
a61af66fc99e Initial load
duke
parents:
diff changeset
356 if (*bot == verify_card)
a61af66fc99e Initial load
duke
parents:
diff changeset
357 *bot = youngergen_card;
a61af66fc99e Initial load
duke
parents:
diff changeset
358 bot++;
a61af66fc99e Initial load
duke
parents:
diff changeset
359 }
a61af66fc99e Initial load
duke
parents:
diff changeset
360 }
a61af66fc99e Initial load
duke
parents:
diff changeset
361
a61af66fc99e Initial load
duke
parents:
diff changeset
362 bool CardTableExtension::addr_is_marked_imprecise(void *addr) {
a61af66fc99e Initial load
duke
parents:
diff changeset
363 jbyte* p = byte_for(addr);
a61af66fc99e Initial load
duke
parents:
diff changeset
364 jbyte val = *p;
a61af66fc99e Initial load
duke
parents:
diff changeset
365
a61af66fc99e Initial load
duke
parents:
diff changeset
366 if (card_is_dirty(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
367 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
368
a61af66fc99e Initial load
duke
parents:
diff changeset
369 if (card_is_newgen(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
370 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
371
a61af66fc99e Initial load
duke
parents:
diff changeset
372 if (card_is_clean(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
373 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
374
a61af66fc99e Initial load
duke
parents:
diff changeset
375 assert(false, "Found unhandled card mark type");
a61af66fc99e Initial load
duke
parents:
diff changeset
376
a61af66fc99e Initial load
duke
parents:
diff changeset
377 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
378 }
a61af66fc99e Initial load
duke
parents:
diff changeset
379
a61af66fc99e Initial load
duke
parents:
diff changeset
380 // Also includes verify_card
a61af66fc99e Initial load
duke
parents:
diff changeset
381 bool CardTableExtension::addr_is_marked_precise(void *addr) {
a61af66fc99e Initial load
duke
parents:
diff changeset
382 jbyte* p = byte_for(addr);
a61af66fc99e Initial load
duke
parents:
diff changeset
383 jbyte val = *p;
a61af66fc99e Initial load
duke
parents:
diff changeset
384
a61af66fc99e Initial load
duke
parents:
diff changeset
385 if (card_is_newgen(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
386 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
387
a61af66fc99e Initial load
duke
parents:
diff changeset
388 if (card_is_verify(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
389 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
390
a61af66fc99e Initial load
duke
parents:
diff changeset
391 if (card_is_clean(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
392 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
393
a61af66fc99e Initial load
duke
parents:
diff changeset
394 if (card_is_dirty(val))
a61af66fc99e Initial load
duke
parents:
diff changeset
395 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
396
a61af66fc99e Initial load
duke
parents:
diff changeset
397 assert(false, "Found unhandled card mark type");
a61af66fc99e Initial load
duke
parents:
diff changeset
398
a61af66fc99e Initial load
duke
parents:
diff changeset
399 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
400 }
a61af66fc99e Initial load
duke
parents:
diff changeset
401
a61af66fc99e Initial load
duke
parents:
diff changeset
402 // Assumes that only the base or the end changes. This allows indentification
a61af66fc99e Initial load
duke
parents:
diff changeset
403 // of the region that is being resized. The
a61af66fc99e Initial load
duke
parents:
diff changeset
404 // CardTableModRefBS::resize_covered_region() is used for the normal case
a61af66fc99e Initial load
duke
parents:
diff changeset
405 // where the covered regions are growing or shrinking at the high end.
a61af66fc99e Initial load
duke
parents:
diff changeset
406 // The method resize_covered_region_by_end() is analogous to
a61af66fc99e Initial load
duke
parents:
diff changeset
407 // CardTableModRefBS::resize_covered_region() but
a61af66fc99e Initial load
duke
parents:
diff changeset
408 // for regions that grow or shrink at the low end.
a61af66fc99e Initial load
duke
parents:
diff changeset
409 void CardTableExtension::resize_covered_region(MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
410
a61af66fc99e Initial load
duke
parents:
diff changeset
411 for (int i = 0; i < _cur_covered_regions; i++) {
a61af66fc99e Initial load
duke
parents:
diff changeset
412 if (_covered[i].start() == new_region.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
413 // Found a covered region with the same start as the
a61af66fc99e Initial load
duke
parents:
diff changeset
414 // new region. The region is growing or shrinking
a61af66fc99e Initial load
duke
parents:
diff changeset
415 // from the start of the region.
a61af66fc99e Initial load
duke
parents:
diff changeset
416 resize_covered_region_by_start(new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
417 return;
a61af66fc99e Initial load
duke
parents:
diff changeset
418 }
a61af66fc99e Initial load
duke
parents:
diff changeset
419 if (_covered[i].start() > new_region.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
420 break;
a61af66fc99e Initial load
duke
parents:
diff changeset
421 }
a61af66fc99e Initial load
duke
parents:
diff changeset
422 }
a61af66fc99e Initial load
duke
parents:
diff changeset
423
a61af66fc99e Initial load
duke
parents:
diff changeset
424 int changed_region = -1;
a61af66fc99e Initial load
duke
parents:
diff changeset
425 for (int j = 0; j < _cur_covered_regions; j++) {
a61af66fc99e Initial load
duke
parents:
diff changeset
426 if (_covered[j].end() == new_region.end()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
427 changed_region = j;
a61af66fc99e Initial load
duke
parents:
diff changeset
428 // This is a case where the covered region is growing or shrinking
a61af66fc99e Initial load
duke
parents:
diff changeset
429 // at the start of the region.
a61af66fc99e Initial load
duke
parents:
diff changeset
430 assert(changed_region != -1, "Don't expect to add a covered region");
a61af66fc99e Initial load
duke
parents:
diff changeset
431 assert(_covered[changed_region].byte_size() != new_region.byte_size(),
a61af66fc99e Initial load
duke
parents:
diff changeset
432 "The sizes should be different here");
a61af66fc99e Initial load
duke
parents:
diff changeset
433 resize_covered_region_by_end(changed_region, new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
434 return;
a61af66fc99e Initial load
duke
parents:
diff changeset
435 }
a61af66fc99e Initial load
duke
parents:
diff changeset
436 }
a61af66fc99e Initial load
duke
parents:
diff changeset
437 // This should only be a new covered region (where no existing
a61af66fc99e Initial load
duke
parents:
diff changeset
438 // covered region matches at the start or the end).
a61af66fc99e Initial load
duke
parents:
diff changeset
439 assert(_cur_covered_regions < _max_covered_regions,
a61af66fc99e Initial load
duke
parents:
diff changeset
440 "An existing region should have been found");
a61af66fc99e Initial load
duke
parents:
diff changeset
441 resize_covered_region_by_start(new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
442 }
a61af66fc99e Initial load
duke
parents:
diff changeset
443
a61af66fc99e Initial load
duke
parents:
diff changeset
444 void CardTableExtension::resize_covered_region_by_start(MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
445 CardTableModRefBS::resize_covered_region(new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
446 debug_only(verify_guard();)
a61af66fc99e Initial load
duke
parents:
diff changeset
447 }
a61af66fc99e Initial load
duke
parents:
diff changeset
448
a61af66fc99e Initial load
duke
parents:
diff changeset
449 void CardTableExtension::resize_covered_region_by_end(int changed_region,
a61af66fc99e Initial load
duke
parents:
diff changeset
450 MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
451 assert(SafepointSynchronize::is_at_safepoint(),
a61af66fc99e Initial load
duke
parents:
diff changeset
452 "Only expect an expansion at the low end at a GC");
a61af66fc99e Initial load
duke
parents:
diff changeset
453 debug_only(verify_guard();)
a61af66fc99e Initial load
duke
parents:
diff changeset
454 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
455 for (int k = 0; k < _cur_covered_regions; k++) {
a61af66fc99e Initial load
duke
parents:
diff changeset
456 if (_covered[k].end() == new_region.end()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
457 assert(changed_region == k, "Changed region is incorrect");
a61af66fc99e Initial load
duke
parents:
diff changeset
458 break;
a61af66fc99e Initial load
duke
parents:
diff changeset
459 }
a61af66fc99e Initial load
duke
parents:
diff changeset
460 }
a61af66fc99e Initial load
duke
parents:
diff changeset
461 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
462
a61af66fc99e Initial load
duke
parents:
diff changeset
463 // Commit new or uncommit old pages, if necessary.
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
464 if (resize_commit_uncommit(changed_region, new_region)) {
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
465 // Set the new start of the committed region
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
466 resize_update_committed_table(changed_region, new_region);
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
467 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
468
a61af66fc99e Initial load
duke
parents:
diff changeset
469 // Update card table entries
a61af66fc99e Initial load
duke
parents:
diff changeset
470 resize_update_card_table_entries(changed_region, new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
471
a61af66fc99e Initial load
duke
parents:
diff changeset
472 // Update the covered region
a61af66fc99e Initial load
duke
parents:
diff changeset
473 resize_update_covered_table(changed_region, new_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
474
a61af66fc99e Initial load
duke
parents:
diff changeset
475 if (TraceCardTableModRefBS) {
a61af66fc99e Initial load
duke
parents:
diff changeset
476 int ind = changed_region;
a61af66fc99e Initial load
duke
parents:
diff changeset
477 gclog_or_tty->print_cr("CardTableModRefBS::resize_covered_region: ");
a61af66fc99e Initial load
duke
parents:
diff changeset
478 gclog_or_tty->print_cr(" "
a61af66fc99e Initial load
duke
parents:
diff changeset
479 " _covered[%d].start(): " INTPTR_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
480 " _covered[%d].last(): " INTPTR_FORMAT,
a61af66fc99e Initial load
duke
parents:
diff changeset
481 ind, _covered[ind].start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
482 ind, _covered[ind].last());
a61af66fc99e Initial load
duke
parents:
diff changeset
483 gclog_or_tty->print_cr(" "
a61af66fc99e Initial load
duke
parents:
diff changeset
484 " _committed[%d].start(): " INTPTR_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
485 " _committed[%d].last(): " INTPTR_FORMAT,
a61af66fc99e Initial load
duke
parents:
diff changeset
486 ind, _committed[ind].start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
487 ind, _committed[ind].last());
a61af66fc99e Initial load
duke
parents:
diff changeset
488 gclog_or_tty->print_cr(" "
a61af66fc99e Initial load
duke
parents:
diff changeset
489 " byte_for(start): " INTPTR_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
490 " byte_for(last): " INTPTR_FORMAT,
a61af66fc99e Initial load
duke
parents:
diff changeset
491 byte_for(_covered[ind].start()),
a61af66fc99e Initial load
duke
parents:
diff changeset
492 byte_for(_covered[ind].last()));
a61af66fc99e Initial load
duke
parents:
diff changeset
493 gclog_or_tty->print_cr(" "
a61af66fc99e Initial load
duke
parents:
diff changeset
494 " addr_for(start): " INTPTR_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
495 " addr_for(last): " INTPTR_FORMAT,
a61af66fc99e Initial load
duke
parents:
diff changeset
496 addr_for((jbyte*) _committed[ind].start()),
a61af66fc99e Initial load
duke
parents:
diff changeset
497 addr_for((jbyte*) _committed[ind].last()));
a61af66fc99e Initial load
duke
parents:
diff changeset
498 }
a61af66fc99e Initial load
duke
parents:
diff changeset
499 debug_only(verify_guard();)
a61af66fc99e Initial load
duke
parents:
diff changeset
500 }
a61af66fc99e Initial load
duke
parents:
diff changeset
501
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
502 bool CardTableExtension::resize_commit_uncommit(int changed_region,
0
a61af66fc99e Initial load
duke
parents:
diff changeset
503 MemRegion new_region) {
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
504 bool result = false;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
505 // Commit new or uncommit old pages, if necessary.
a61af66fc99e Initial load
duke
parents:
diff changeset
506 MemRegion cur_committed = _committed[changed_region];
a61af66fc99e Initial load
duke
parents:
diff changeset
507 assert(_covered[changed_region].end() == new_region.end(),
a61af66fc99e Initial load
duke
parents:
diff changeset
508 "The ends of the regions are expected to match");
a61af66fc99e Initial load
duke
parents:
diff changeset
509 // Extend the start of this _committed region to
a61af66fc99e Initial load
duke
parents:
diff changeset
510 // to cover the start of any previous _committed region.
a61af66fc99e Initial load
duke
parents:
diff changeset
511 // This forms overlapping regions, but never interior regions.
a61af66fc99e Initial load
duke
parents:
diff changeset
512 HeapWord* min_prev_start = lowest_prev_committed_start(changed_region);
a61af66fc99e Initial load
duke
parents:
diff changeset
513 if (min_prev_start < cur_committed.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
514 // Only really need to set start of "cur_committed" to
a61af66fc99e Initial load
duke
parents:
diff changeset
515 // the new start (min_prev_start) but assertion checking code
a61af66fc99e Initial load
duke
parents:
diff changeset
516 // below use cur_committed.end() so make it correct.
a61af66fc99e Initial load
duke
parents:
diff changeset
517 MemRegion new_committed =
a61af66fc99e Initial load
duke
parents:
diff changeset
518 MemRegion(min_prev_start, cur_committed.end());
a61af66fc99e Initial load
duke
parents:
diff changeset
519 cur_committed = new_committed;
a61af66fc99e Initial load
duke
parents:
diff changeset
520 }
a61af66fc99e Initial load
duke
parents:
diff changeset
521 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
522 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
523 assert(cur_committed.start() ==
a61af66fc99e Initial load
duke
parents:
diff changeset
524 (HeapWord*) align_size_up((uintptr_t) cur_committed.start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
525 os::vm_page_size()),
a61af66fc99e Initial load
duke
parents:
diff changeset
526 "Starts should have proper alignment");
a61af66fc99e Initial load
duke
parents:
diff changeset
527 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
528
a61af66fc99e Initial load
duke
parents:
diff changeset
529 jbyte* new_start = byte_for(new_region.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
530 // Round down because this is for the start address
a61af66fc99e Initial load
duke
parents:
diff changeset
531 HeapWord* new_start_aligned =
a61af66fc99e Initial load
duke
parents:
diff changeset
532 (HeapWord*)align_size_down((uintptr_t)new_start, os::vm_page_size());
a61af66fc99e Initial load
duke
parents:
diff changeset
533 // The guard page is always committed and should not be committed over.
a61af66fc99e Initial load
duke
parents:
diff changeset
534 // This method is used in cases where the generation is growing toward
a61af66fc99e Initial load
duke
parents:
diff changeset
535 // lower addresses but the guard region is still at the end of the
a61af66fc99e Initial load
duke
parents:
diff changeset
536 // card table. That still makes sense when looking for writes
a61af66fc99e Initial load
duke
parents:
diff changeset
537 // off the end of the card table.
a61af66fc99e Initial load
duke
parents:
diff changeset
538 if (new_start_aligned < cur_committed.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
539 // Expand the committed region
a61af66fc99e Initial load
duke
parents:
diff changeset
540 //
a61af66fc99e Initial load
duke
parents:
diff changeset
541 // Case A
a61af66fc99e Initial load
duke
parents:
diff changeset
542 // |+ guard +|
a61af66fc99e Initial load
duke
parents:
diff changeset
543 // |+ cur committed +++++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
544 // |+ new committed +++++++++++++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
545 //
a61af66fc99e Initial load
duke
parents:
diff changeset
546 // Case B
a61af66fc99e Initial load
duke
parents:
diff changeset
547 // |+ guard +|
a61af66fc99e Initial load
duke
parents:
diff changeset
548 // |+ cur committed +|
a61af66fc99e Initial load
duke
parents:
diff changeset
549 // |+ new committed +++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
550 //
a61af66fc99e Initial load
duke
parents:
diff changeset
551 // These are not expected because the calculation of the
a61af66fc99e Initial load
duke
parents:
diff changeset
552 // cur committed region and the new committed region
a61af66fc99e Initial load
duke
parents:
diff changeset
553 // share the same end for the covered region.
a61af66fc99e Initial load
duke
parents:
diff changeset
554 // Case C
a61af66fc99e Initial load
duke
parents:
diff changeset
555 // |+ guard +|
a61af66fc99e Initial load
duke
parents:
diff changeset
556 // |+ cur committed +|
a61af66fc99e Initial load
duke
parents:
diff changeset
557 // |+ new committed +++++++++++++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
558 // Case D
a61af66fc99e Initial load
duke
parents:
diff changeset
559 // |+ guard +|
a61af66fc99e Initial load
duke
parents:
diff changeset
560 // |+ cur committed +++++++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
561 // |+ new committed +++++++|
a61af66fc99e Initial load
duke
parents:
diff changeset
562
a61af66fc99e Initial load
duke
parents:
diff changeset
563 HeapWord* new_end_for_commit =
a61af66fc99e Initial load
duke
parents:
diff changeset
564 MIN2(cur_committed.end(), _guard_region.start());
263
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
565 if(new_start_aligned < new_end_for_commit) {
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
566 MemRegion new_committed =
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
567 MemRegion(new_start_aligned, new_end_for_commit);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
568 if (!os::commit_memory((char*)new_committed.start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
569 new_committed.byte_size())) {
a61af66fc99e Initial load
duke
parents:
diff changeset
570 vm_exit_out_of_memory(new_committed.byte_size(),
a61af66fc99e Initial load
duke
parents:
diff changeset
571 "card table expansion");
a61af66fc99e Initial load
duke
parents:
diff changeset
572 }
a61af66fc99e Initial load
duke
parents:
diff changeset
573 }
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
574 result = true;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
575 } else if (new_start_aligned > cur_committed.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
576 // Shrink the committed region
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
577 #if 0 // uncommitting space is currently unsafe because of the interactions
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
578 // of growing and shrinking regions. One region A can uncommit space
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
579 // that it owns but which is being used by another region B (maybe).
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
580 // Region B has not committed the space because it was already
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
581 // committed by region A.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
582 MemRegion uncommit_region = committed_unique_to_self(changed_region,
a61af66fc99e Initial load
duke
parents:
diff changeset
583 MemRegion(cur_committed.start(), new_start_aligned));
a61af66fc99e Initial load
duke
parents:
diff changeset
584 if (!uncommit_region.is_empty()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
585 if (!os::uncommit_memory((char*)uncommit_region.start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
586 uncommit_region.byte_size())) {
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
587 // If the uncommit fails, ignore it. Let the
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
588 // committed table resizing go even though the committed
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
589 // table will over state the committed space.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
590 }
a61af66fc99e Initial load
duke
parents:
diff changeset
591 }
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
592 #else
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
593 assert(!result, "Should be false with current workaround");
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
594 #endif
0
a61af66fc99e Initial load
duke
parents:
diff changeset
595 }
a61af66fc99e Initial load
duke
parents:
diff changeset
596 assert(_committed[changed_region].end() == cur_committed.end(),
a61af66fc99e Initial load
duke
parents:
diff changeset
597 "end should not change");
1612
fdde661c8e06 6952853: SIGSEGV with UseAdaptiveGCBoundary on 64b linux running jvm2008
jmasa
parents: 1552
diff changeset
598 return result;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
599 }
a61af66fc99e Initial load
duke
parents:
diff changeset
600
a61af66fc99e Initial load
duke
parents:
diff changeset
601 void CardTableExtension::resize_update_committed_table(int changed_region,
a61af66fc99e Initial load
duke
parents:
diff changeset
602 MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
603
a61af66fc99e Initial load
duke
parents:
diff changeset
604 jbyte* new_start = byte_for(new_region.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
605 // Set the new start of the committed region
a61af66fc99e Initial load
duke
parents:
diff changeset
606 HeapWord* new_start_aligned =
a61af66fc99e Initial load
duke
parents:
diff changeset
607 (HeapWord*)align_size_down((uintptr_t)new_start,
a61af66fc99e Initial load
duke
parents:
diff changeset
608 os::vm_page_size());
a61af66fc99e Initial load
duke
parents:
diff changeset
609 MemRegion new_committed = MemRegion(new_start_aligned,
a61af66fc99e Initial load
duke
parents:
diff changeset
610 _committed[changed_region].end());
a61af66fc99e Initial load
duke
parents:
diff changeset
611 _committed[changed_region] = new_committed;
a61af66fc99e Initial load
duke
parents:
diff changeset
612 _committed[changed_region].set_start(new_start_aligned);
a61af66fc99e Initial load
duke
parents:
diff changeset
613 }
a61af66fc99e Initial load
duke
parents:
diff changeset
614
a61af66fc99e Initial load
duke
parents:
diff changeset
615 void CardTableExtension::resize_update_card_table_entries(int changed_region,
a61af66fc99e Initial load
duke
parents:
diff changeset
616 MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
617 debug_only(verify_guard();)
a61af66fc99e Initial load
duke
parents:
diff changeset
618 MemRegion original_covered = _covered[changed_region];
a61af66fc99e Initial load
duke
parents:
diff changeset
619 // Initialize the card entries. Only consider the
a61af66fc99e Initial load
duke
parents:
diff changeset
620 // region covered by the card table (_whole_heap)
a61af66fc99e Initial load
duke
parents:
diff changeset
621 jbyte* entry;
a61af66fc99e Initial load
duke
parents:
diff changeset
622 if (new_region.start() < _whole_heap.start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
623 entry = byte_for(_whole_heap.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
624 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
625 entry = byte_for(new_region.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
626 }
a61af66fc99e Initial load
duke
parents:
diff changeset
627 jbyte* end = byte_for(original_covered.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
628 // If _whole_heap starts at the original covered regions start,
a61af66fc99e Initial load
duke
parents:
diff changeset
629 // this loop will not execute.
a61af66fc99e Initial load
duke
parents:
diff changeset
630 while (entry < end) { *entry++ = clean_card; }
a61af66fc99e Initial load
duke
parents:
diff changeset
631 }
a61af66fc99e Initial load
duke
parents:
diff changeset
632
a61af66fc99e Initial load
duke
parents:
diff changeset
633 void CardTableExtension::resize_update_covered_table(int changed_region,
a61af66fc99e Initial load
duke
parents:
diff changeset
634 MemRegion new_region) {
a61af66fc99e Initial load
duke
parents:
diff changeset
635 // Update the covered region
a61af66fc99e Initial load
duke
parents:
diff changeset
636 _covered[changed_region].set_start(new_region.start());
a61af66fc99e Initial load
duke
parents:
diff changeset
637 _covered[changed_region].set_word_size(new_region.word_size());
a61af66fc99e Initial load
duke
parents:
diff changeset
638
a61af66fc99e Initial load
duke
parents:
diff changeset
639 // reorder regions. There should only be at most 1 out
a61af66fc99e Initial load
duke
parents:
diff changeset
640 // of order.
a61af66fc99e Initial load
duke
parents:
diff changeset
641 for (int i = _cur_covered_regions-1 ; i > 0; i--) {
a61af66fc99e Initial load
duke
parents:
diff changeset
642 if (_covered[i].start() < _covered[i-1].start()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
643 MemRegion covered_mr = _covered[i-1];
a61af66fc99e Initial load
duke
parents:
diff changeset
644 _covered[i-1] = _covered[i];
a61af66fc99e Initial load
duke
parents:
diff changeset
645 _covered[i] = covered_mr;
a61af66fc99e Initial load
duke
parents:
diff changeset
646 MemRegion committed_mr = _committed[i-1];
a61af66fc99e Initial load
duke
parents:
diff changeset
647 _committed[i-1] = _committed[i];
a61af66fc99e Initial load
duke
parents:
diff changeset
648 _committed[i] = committed_mr;
a61af66fc99e Initial load
duke
parents:
diff changeset
649 break;
a61af66fc99e Initial load
duke
parents:
diff changeset
650 }
a61af66fc99e Initial load
duke
parents:
diff changeset
651 }
a61af66fc99e Initial load
duke
parents:
diff changeset
652 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
653 for (int m = 0; m < _cur_covered_regions-1; m++) {
a61af66fc99e Initial load
duke
parents:
diff changeset
654 assert(_covered[m].start() <= _covered[m+1].start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
655 "Covered regions out of order");
a61af66fc99e Initial load
duke
parents:
diff changeset
656 assert(_committed[m].start() <= _committed[m+1].start(),
a61af66fc99e Initial load
duke
parents:
diff changeset
657 "Committed regions out of order");
a61af66fc99e Initial load
duke
parents:
diff changeset
658 }
a61af66fc99e Initial load
duke
parents:
diff changeset
659 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
660 }
a61af66fc99e Initial load
duke
parents:
diff changeset
661
a61af66fc99e Initial load
duke
parents:
diff changeset
662 // Returns the start of any committed region that is lower than
a61af66fc99e Initial load
duke
parents:
diff changeset
663 // the target committed region (index ind) and that intersects the
a61af66fc99e Initial load
duke
parents:
diff changeset
664 // target region. If none, return start of target region.
a61af66fc99e Initial load
duke
parents:
diff changeset
665 //
a61af66fc99e Initial load
duke
parents:
diff changeset
666 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
667 // | |
a61af66fc99e Initial load
duke
parents:
diff changeset
668 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
669 // ------------
a61af66fc99e Initial load
duke
parents:
diff changeset
670 // | target |
a61af66fc99e Initial load
duke
parents:
diff changeset
671 // ------------
a61af66fc99e Initial load
duke
parents:
diff changeset
672 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
673 // | |
a61af66fc99e Initial load
duke
parents:
diff changeset
674 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
675 // ^ returns this
a61af66fc99e Initial load
duke
parents:
diff changeset
676 //
a61af66fc99e Initial load
duke
parents:
diff changeset
677 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
678 // | |
a61af66fc99e Initial load
duke
parents:
diff changeset
679 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
680 // ------------
a61af66fc99e Initial load
duke
parents:
diff changeset
681 // | target |
a61af66fc99e Initial load
duke
parents:
diff changeset
682 // ------------
a61af66fc99e Initial load
duke
parents:
diff changeset
683 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
684 // | |
a61af66fc99e Initial load
duke
parents:
diff changeset
685 // -------------
a61af66fc99e Initial load
duke
parents:
diff changeset
686 // ^ returns this
a61af66fc99e Initial load
duke
parents:
diff changeset
687
a61af66fc99e Initial load
duke
parents:
diff changeset
688 HeapWord* CardTableExtension::lowest_prev_committed_start(int ind) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
689 assert(_cur_covered_regions >= 0, "Expecting at least on region");
a61af66fc99e Initial load
duke
parents:
diff changeset
690 HeapWord* min_start = _committed[ind].start();
a61af66fc99e Initial load
duke
parents:
diff changeset
691 for (int j = 0; j < ind; j++) {
a61af66fc99e Initial load
duke
parents:
diff changeset
692 HeapWord* this_start = _committed[j].start();
a61af66fc99e Initial load
duke
parents:
diff changeset
693 if ((this_start < min_start) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
694 !(_committed[j].intersection(_committed[ind])).is_empty()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
695 min_start = this_start;
a61af66fc99e Initial load
duke
parents:
diff changeset
696 }
a61af66fc99e Initial load
duke
parents:
diff changeset
697 }
a61af66fc99e Initial load
duke
parents:
diff changeset
698 return min_start;
a61af66fc99e Initial load
duke
parents:
diff changeset
699 }