21 * questions. |
21 * questions. |
22 */ |
22 */ |
23 |
23 |
24 #include "precompiled.hpp" |
24 #include "precompiled.hpp" |
25 #include "classfile/classLoaderData.hpp" |
25 #include "classfile/classLoaderData.hpp" |
26 #include "classfile/classLoaderDataGraph.hpp" |
|
27 #include "gc/z/zAddress.hpp" |
26 #include "gc/z/zAddress.hpp" |
28 #include "gc/z/zHeap.inline.hpp" |
27 #include "gc/z/zHeap.inline.hpp" |
29 #include "gc/z/zOop.hpp" |
28 #include "gc/z/zOop.hpp" |
30 #include "gc/z/zResurrection.hpp" |
29 #include "gc/z/zResurrection.hpp" |
31 #include "gc/z/zRootsIterator.hpp" |
30 #include "gc/z/zRootsIterator.hpp" |
32 #include "gc/z/zStat.hpp" |
31 #include "gc/z/zStat.hpp" |
33 #include "gc/z/zVerify.hpp" |
32 #include "gc/z/zVerify.hpp" |
34 #include "memory/allocation.hpp" |
|
35 #include "memory/iterator.inline.hpp" |
33 #include "memory/iterator.inline.hpp" |
36 #include "oops/oop.inline.hpp" |
34 #include "oops/oop.hpp" |
37 |
35 |
38 #define BAD_OOP_REPORT(addr) \ |
36 #define BAD_OOP_ARG(o, p) "Bad oop " PTR_FORMAT " found at " PTR_FORMAT, p2i(o), p2i(p) |
39 "Bad oop " PTR_FORMAT " found at " PTR_FORMAT ", expected " PTR_FORMAT, \ |
|
40 addr, p2i(p), ZAddress::good(addr) |
|
41 |
37 |
42 class ZVerifyRootsClosure : public ZRootsIteratorClosure { |
38 static void verify_oop(oop* p) { |
|
39 const oop o = RawAccess<>::oop_load(p); |
|
40 if (o != NULL) { |
|
41 const uintptr_t addr = ZOop::to_address(o); |
|
42 guarantee(ZAddress::is_good(addr), BAD_OOP_ARG(o, p)); |
|
43 guarantee(oopDesc::is_oop(ZOop::from_address(addr)), BAD_OOP_ARG(o, p)); |
|
44 } |
|
45 } |
|
46 |
|
47 static void verify_possibly_weak_oop(oop* p) { |
|
48 const oop o = RawAccess<>::oop_load(p); |
|
49 if (o != NULL) { |
|
50 const uintptr_t addr = ZOop::to_address(o); |
|
51 guarantee(ZAddress::is_good(addr) || ZAddress::is_finalizable_good(addr), BAD_OOP_ARG(o, p)); |
|
52 guarantee(oopDesc::is_oop(ZOop::from_address(ZAddress::good(addr))), BAD_OOP_ARG(o, p)); |
|
53 } |
|
54 } |
|
55 |
|
56 class ZVerifyRootClosure : public ZRootsIteratorClosure { |
43 public: |
57 public: |
44 virtual void do_oop(oop* p) { |
58 virtual void do_oop(oop* p) { |
45 uintptr_t value = ZOop::to_address(*p); |
59 verify_oop(p); |
|
60 } |
46 |
61 |
47 if (value == 0) { |
62 virtual void do_oop(narrowOop*) { |
48 return; |
63 ShouldNotReachHere(); |
49 } |
|
50 |
|
51 guarantee(!ZAddress::is_finalizable(value), BAD_OOP_REPORT(value)); |
|
52 guarantee(ZAddress::is_good(value), BAD_OOP_REPORT(value)); |
|
53 guarantee(oopDesc::is_oop(ZOop::from_address(value)), BAD_OOP_REPORT(value)); |
|
54 } |
64 } |
55 virtual void do_oop(narrowOop*) { ShouldNotReachHere(); } |
|
56 }; |
65 }; |
57 |
66 |
58 template <bool VisitReferents> |
|
59 class ZVerifyOopClosure : public ClaimMetadataVisitingOopIterateClosure, public ZRootsIteratorClosure { |
67 class ZVerifyOopClosure : public ClaimMetadataVisitingOopIterateClosure, public ZRootsIteratorClosure { |
|
68 private: |
|
69 const bool _verify_weaks; |
|
70 |
60 public: |
71 public: |
61 ZVerifyOopClosure() : |
72 ZVerifyOopClosure(bool verify_weaks) : |
62 ClaimMetadataVisitingOopIterateClosure(ClassLoaderData::_claim_other) {} |
73 ClaimMetadataVisitingOopIterateClosure(ClassLoaderData::_claim_other), |
|
74 _verify_weaks(verify_weaks) {} |
63 |
75 |
64 virtual void do_oop(oop* p); |
76 virtual void do_oop(oop* p) { |
65 virtual void do_oop(narrowOop* p) { ShouldNotReachHere(); } |
77 if (_verify_weaks) { |
|
78 verify_possibly_weak_oop(p); |
|
79 } else { |
|
80 // We should never encounter finalizable oops through strong |
|
81 // paths. This assumes we have only visited strong roots. |
|
82 verify_oop(p); |
|
83 } |
|
84 } |
|
85 |
|
86 virtual void do_oop(narrowOop* p) { |
|
87 ShouldNotReachHere(); |
|
88 } |
66 |
89 |
67 virtual ReferenceIterationMode reference_iteration_mode() { |
90 virtual ReferenceIterationMode reference_iteration_mode() { |
68 return VisitReferents ? DO_FIELDS : DO_FIELDS_EXCEPT_REFERENT; |
91 return _verify_weaks ? DO_FIELDS : DO_FIELDS_EXCEPT_REFERENT; |
69 } |
92 } |
70 |
93 |
71 #ifdef ASSERT |
94 #ifdef ASSERT |
72 // Verification handled by the closure itself |
95 // Verification handled by the closure itself |
73 virtual bool should_verify_oops() { |
96 virtual bool should_verify_oops() { |
74 return false; |
97 return false; |
75 } |
98 } |
76 #endif |
99 #endif |
77 }; |
100 }; |
78 |
101 |
79 class ZVerifyObjectClosure : public ObjectClosure { |
102 template <typename RootsIterator> |
80 private: |
103 void ZVerify::roots() { |
81 bool _visit_referents; |
104 assert(SafepointSynchronize::is_at_safepoint(), "Must be at a safepoint"); |
|
105 assert(!ZResurrection::is_blocked(), "Invalid phase"); |
82 |
106 |
83 public: |
|
84 ZVerifyObjectClosure(bool visit_referents) : _visit_referents(visit_referents) {} |
|
85 virtual void do_object(oop o); |
|
86 }; |
|
87 |
|
88 template <typename RootsIterator> |
|
89 void ZVerify::roots_impl() { |
|
90 if (ZVerifyRoots) { |
107 if (ZVerifyRoots) { |
91 ZVerifyRootsClosure cl; |
108 ZVerifyRootClosure cl; |
92 RootsIterator iter; |
109 RootsIterator iter; |
93 iter.oops_do(&cl); |
110 iter.oops_do(&cl); |
94 } |
111 } |
95 } |
112 } |
96 |
113 |
97 void ZVerify::roots_strong() { |
114 void ZVerify::roots_strong() { |
98 roots_impl<ZRootsIterator>(); |
115 roots<ZRootsIterator>(); |
99 } |
|
100 |
|
101 class ZVerifyConcurrentRootsIterator : public ZConcurrentRootsIterator { |
|
102 public: |
|
103 ZVerifyConcurrentRootsIterator() |
|
104 : ZConcurrentRootsIterator(ClassLoaderData::_claim_none) {} |
|
105 }; |
|
106 |
|
107 void ZVerify::roots_concurrent() { |
|
108 roots_impl<ZVerifyConcurrentRootsIterator>(); |
|
109 } |
116 } |
110 |
117 |
111 void ZVerify::roots_weak() { |
118 void ZVerify::roots_weak() { |
112 assert(!ZResurrection::is_blocked(), "Invalid phase"); |
119 roots<ZWeakRootsIterator>(); |
|
120 } |
113 |
121 |
114 roots_impl<ZWeakRootsIterator>(); |
122 void ZVerify::roots_concurrent_strong() { |
|
123 roots<ZConcurrentRootsIteratorClaimNone>(); |
|
124 } |
|
125 |
|
126 void ZVerify::roots_concurrent_weak() { |
|
127 roots<ZConcurrentWeakRootsIterator>(); |
115 } |
128 } |
116 |
129 |
117 void ZVerify::roots(bool verify_weaks) { |
130 void ZVerify::roots(bool verify_weaks) { |
118 roots_strong(); |
131 roots_strong(); |
119 roots_concurrent(); |
132 roots_concurrent_strong(); |
120 if (verify_weaks) { |
133 if (verify_weaks) { |
121 roots_weak(); |
134 roots_weak(); |
122 roots_concurrent_weak(); |
135 roots_concurrent_weak(); |
123 } |
136 } |
124 } |
137 } |
125 |
138 |
126 void ZVerify::objects(bool verify_weaks) { |
139 void ZVerify::objects(bool verify_weaks) { |
|
140 assert(SafepointSynchronize::is_at_safepoint(), "Must be at a safepoint"); |
|
141 assert(ZGlobalPhase == ZPhaseMarkCompleted, "Invalid phase"); |
|
142 assert(!ZResurrection::is_blocked(), "Invalid phase"); |
|
143 |
127 if (ZVerifyObjects) { |
144 if (ZVerifyObjects) { |
128 ZVerifyObjectClosure cl(verify_weaks); |
145 ZVerifyOopClosure cl(verify_weaks); |
129 ZHeap::heap()->object_iterate(&cl, verify_weaks); |
146 ObjectToOopClosure object_cl(&cl); |
|
147 ZHeap::heap()->object_iterate(&object_cl, verify_weaks); |
130 } |
148 } |
131 } |
149 } |
132 |
150 |
133 void ZVerify::roots_concurrent_weak() { |
|
134 assert(!ZResurrection::is_blocked(), "Invalid phase"); |
|
135 |
|
136 roots_impl<ZConcurrentWeakRootsIterator>(); |
|
137 } |
|
138 |
|
139 void ZVerify::roots_and_objects(bool verify_weaks) { |
151 void ZVerify::roots_and_objects(bool verify_weaks) { |
140 ZStatTimerDisable _disable; |
|
141 |
|
142 roots(verify_weaks); |
152 roots(verify_weaks); |
143 objects(verify_weaks); |
153 objects(verify_weaks); |
144 } |
154 } |
145 |
155 |
146 void ZVerify::before_zoperation() { |
156 void ZVerify::before_zoperation() { |
148 ZStatTimerDisable disable; |
158 ZStatTimerDisable disable; |
149 roots_strong(); |
159 roots_strong(); |
150 } |
160 } |
151 |
161 |
152 void ZVerify::after_mark() { |
162 void ZVerify::after_mark() { |
153 // Only verify strong roots and references. |
163 // Verify all strong roots and strong references |
|
164 ZStatTimerDisable disable; |
154 roots_and_objects(false /* verify_weaks */); |
165 roots_and_objects(false /* verify_weaks */); |
155 } |
166 } |
156 |
167 |
157 void ZVerify::after_weak_processing() { |
168 void ZVerify::after_weak_processing() { |
158 // Also verify weaks - all should have been processed at this point. |
169 // Verify all roots and all references |
|
170 ZStatTimerDisable disable; |
159 roots_and_objects(true /* verify_weaks */); |
171 roots_and_objects(true /* verify_weaks */); |
160 } |
172 } |
161 |
|
162 template <bool VisitReferents> |
|
163 void ZVerifyOopClosure<VisitReferents>::do_oop(oop* p) { |
|
164 guarantee(SafepointSynchronize::is_at_safepoint(), "Must be at a safepoint"); |
|
165 guarantee(ZGlobalPhase == ZPhaseMarkCompleted, "Invalid phase"); |
|
166 guarantee(!ZResurrection::is_blocked(), "Invalid phase"); |
|
167 |
|
168 const oop o = RawAccess<>::oop_load(p); |
|
169 if (o == NULL) { |
|
170 return; |
|
171 } |
|
172 |
|
173 const uintptr_t addr = ZOop::to_address(o); |
|
174 if (VisitReferents) { |
|
175 guarantee(ZAddress::is_good(addr) || ZAddress::is_finalizable_good(addr), BAD_OOP_REPORT(addr)); |
|
176 } else { |
|
177 // Should not encounter finalizable oops through strong-only paths. Assumes only strong roots are visited. |
|
178 guarantee(ZAddress::is_good(addr), BAD_OOP_REPORT(addr)); |
|
179 } |
|
180 |
|
181 const uintptr_t good_addr = ZAddress::good(addr); |
|
182 guarantee(oopDesc::is_oop(ZOop::from_address(good_addr)), BAD_OOP_REPORT(addr)); |
|
183 } |
|
184 |
|
185 void ZVerifyObjectClosure::do_object(oop o) { |
|
186 if (_visit_referents) { |
|
187 ZVerifyOopClosure<true /* VisitReferents */> cl; |
|
188 o->oop_iterate((OopIterateClosure*)&cl); |
|
189 } else { |
|
190 ZVerifyOopClosure<false /* VisitReferents */> cl; |
|
191 o->oop_iterate(&cl); |
|
192 } |
|
193 } |
|