summaryrefslogtreecommitdiff
path: root/runtime/entrypoints/entrypoint_utils.h
diff options
context:
space:
mode:
author Ian Rogers <irogers@google.com> 2014-06-18 16:07:20 -0700
committer Ian Rogers <irogers@google.com> 2014-06-18 16:39:29 -0700
commit6c5cb212fa7010ae7caf9dc765533aa967c95342 (patch)
treec31c46eb7b284b317455fdab48317de92b81dd28 /runtime/entrypoints/entrypoint_utils.h
parent241fd1192dfc0f7322660343179f9fc0591ed9ff (diff)
Ensure classes are initialized rather than initializing.
A class can be being initialized on a different thread, in that case other threads should block trying to access the class. The initializing state shows the class is being initialized but not that its safe for other threads to access. Change occurances of IsInitializing to IsInitialized primarily in slow-path code. Bug: 15347354 Change-Id: Ib586d0a385be6086a890dfbf8868d76f16767fac
Diffstat (limited to 'runtime/entrypoints/entrypoint_utils.h')
-rw-r--r--runtime/entrypoints/entrypoint_utils.h23
1 files changed, 13 insertions, 10 deletions
diff --git a/runtime/entrypoints/entrypoint_utils.h b/runtime/entrypoints/entrypoint_utils.h
index 3d8b29fd24..ff836a4745 100644
--- a/runtime/entrypoints/entrypoint_utils.h
+++ b/runtime/entrypoints/entrypoint_utils.h
@@ -511,13 +511,8 @@ static inline mirror::ArtField* FindFieldFast(uint32_t field_idx,
SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
mirror::ArtField* resolved_field =
referrer->GetDeclaringClass()->GetDexCache()->GetResolvedField(field_idx);
- if (UNLIKELY(resolved_field == NULL)) {
- return NULL;
- }
- mirror::Class* fields_class = resolved_field->GetDeclaringClass();
- // Check class is initiliazed or initializing.
- if (UNLIKELY(!fields_class->IsInitializing())) {
- return NULL;
+ if (UNLIKELY(resolved_field == nullptr)) {
+ return nullptr;
}
// Check for incompatible class change.
bool is_primitive;
@@ -541,7 +536,15 @@ static inline mirror::ArtField* FindFieldFast(uint32_t field_idx,
}
if (UNLIKELY(resolved_field->IsStatic() != is_static)) {
// Incompatible class change.
- return NULL;
+ return nullptr;
+ }
+ mirror::Class* fields_class = resolved_field->GetDeclaringClass();
+ if (is_static) {
+ // Check class is initialized else fail so that we can contend to initialize the class with
+ // other threads that may be racing to do this.
+ if (UNLIKELY(!fields_class->IsInitialized())) {
+ return nullptr;
+ }
}
mirror::Class* referring_class = referrer->GetDeclaringClass();
if (UNLIKELY(!referring_class->CanAccess(fields_class) ||
@@ -549,11 +552,11 @@ static inline mirror::ArtField* FindFieldFast(uint32_t field_idx,
resolved_field->GetAccessFlags()) ||
(is_set && resolved_field->IsFinal() && (fields_class != referring_class)))) {
// Illegal access.
- return NULL;
+ return nullptr;
}
if (UNLIKELY(resolved_field->IsPrimitiveType() != is_primitive ||
resolved_field->FieldSize() != expected_size)) {
- return NULL;
+ return nullptr;
}
return resolved_field;
}