summaryrefslogtreecommitdiff
path: root/runtime/gc/reference_queue.cc
diff options
context:
space:
mode:
author Hiroshi Yamauchi <yamauchi@google.com> 2017-01-12 18:58:38 +0000
committer Gerrit Code Review <noreply-gerritcodereview@google.com> 2017-01-12 18:58:39 +0000
commit9e68f5043323eaf4543ebf3b6f496145d8ae77a2 (patch)
treebc6b03ddb6a20697709d92151a188c1f17458a25 /runtime/gc/reference_queue.cc
parent7620a3b58a9286fae376f4705b602310e5fd464a (diff)
parent65f5f247a367af9d6b9ac63767b69ecf3ab079bc (diff)
Merge "Fix race condition btw DelayReferenceRefernent vs Reference.clear()."
Diffstat (limited to 'runtime/gc/reference_queue.cc')
-rw-r--r--runtime/gc/reference_queue.cc10
1 files changed, 6 insertions, 4 deletions
diff --git a/runtime/gc/reference_queue.cc b/runtime/gc/reference_queue.cc
index a0eb197bd5..734caea371 100644
--- a/runtime/gc/reference_queue.cc
+++ b/runtime/gc/reference_queue.cc
@@ -129,8 +129,9 @@ void ReferenceQueue::ClearWhiteReferences(ReferenceQueue* cleared_references,
while (!IsEmpty()) {
ObjPtr<mirror::Reference> ref = DequeuePendingReference();
mirror::HeapReference<mirror::Object>* referent_addr = ref->GetReferentReferenceAddr();
- if (referent_addr->AsMirrorPtr() != nullptr &&
- !collector->IsMarkedHeapReference(referent_addr)) {
+ // do_atomic_update is false because this happens during the reference processing phase where
+ // Reference.clear() would block.
+ if (!collector->IsNullOrMarkedHeapReference(referent_addr, /*do_atomic_update*/false)) {
// Referent is white, clear it.
if (Runtime::Current()->IsActiveTransaction()) {
ref->ClearReferent<true>();
@@ -147,8 +148,9 @@ void ReferenceQueue::EnqueueFinalizerReferences(ReferenceQueue* cleared_referenc
while (!IsEmpty()) {
ObjPtr<mirror::FinalizerReference> ref = DequeuePendingReference()->AsFinalizerReference();
mirror::HeapReference<mirror::Object>* referent_addr = ref->GetReferentReferenceAddr();
- if (referent_addr->AsMirrorPtr() != nullptr &&
- !collector->IsMarkedHeapReference(referent_addr)) {
+ // do_atomic_update is false because this happens during the reference processing phase where
+ // Reference.clear() would block.
+ if (!collector->IsNullOrMarkedHeapReference(referent_addr, /*do_atomic_update*/false)) {
ObjPtr<mirror::Object> forward_address = collector->MarkObject(referent_addr->AsMirrorPtr());
// Move the updated referent to the zombie field.
if (Runtime::Current()->IsActiveTransaction()) {