This fixes the second crash trace in
33389022#1.
Load the referent once which avoids passing nullptr to IsMarked().
It's still racey but it's okay because leaving a Reference with a
cleared referent gray is fine, if not optimal performance-wise.
Bug:
33389022
Bug:
12687968
Test: test-art-host with CC. 152 in a loop.
Change-Id: I2b389022175e38bdc40518b9553a2f5180dbc649
<< " is_marked=" << IsMarked(to_ref);
}
#ifdef USE_BAKER_OR_BROOKS_READ_BARRIER
+ mirror::Object* referent = nullptr;
if (UNLIKELY((to_ref->GetClass<kVerifyNone, kWithoutReadBarrier>()->IsTypeOfReferenceClass() &&
- to_ref->AsReference()->GetReferent<kWithoutReadBarrier>() != nullptr &&
- !IsInToSpace(to_ref->AsReference()->GetReferent<kWithoutReadBarrier>())))) {
+ (referent = to_ref->AsReference()->GetReferent<kWithoutReadBarrier>()) != nullptr &&
+ !IsInToSpace(referent)))) {
// Leave this reference gray in the queue so that GetReferent() will trigger a read barrier. We
// will change it to white later in ReferenceQueue::DequeuePendingReference().
DCHECK(to_ref->AsReference()->GetPendingNext() != nullptr) << "Left unenqueued ref gray " << to_ref;