src/hotspot/share/opto/parse3.cpp
changeset 55110 17f85a8780d5
parent 53632 d620a4a1d5ed
child 58273 08a5148e7c4e
--- a/src/hotspot/share/opto/parse3.cpp	Thu May 30 09:24:13 2019 -0400
+++ b/src/hotspot/share/opto/parse3.cpp	Thu May 30 19:12:11 2019 +0300
@@ -40,39 +40,6 @@
 //=============================================================================
 // Helper methods for _get* and _put* bytecodes
 //=============================================================================
-bool Parse::static_field_ok_in_clinit(ciField *field, ciMethod *method) {
-  // Could be the field_holder's <clinit> method, or <clinit> for a subklass.
-  // Better to check now than to Deoptimize as soon as we execute
-  assert( field->is_static(), "Only check if field is static");
-  // is_being_initialized() is too generous.  It allows access to statics
-  // by threads that are not running the <clinit> before the <clinit> finishes.
-  // return field->holder()->is_being_initialized();
-
-  // The following restriction is correct but conservative.
-  // It is also desirable to allow compilation of methods called from <clinit>
-  // but this generated code will need to be made safe for execution by
-  // other threads, or the transition from interpreted to compiled code would
-  // need to be guarded.
-  ciInstanceKlass *field_holder = field->holder();
-
-  if (method->holder()->is_subclass_of(field_holder)) {
-    if (method->is_static_initializer()) {
-      // OK to access static fields inside initializer
-      return true;
-    } else if (method->is_object_initializer()) {
-      // It's also OK to access static fields inside a constructor,
-      // because any thread calling the constructor must first have
-      // synchronized on the class by executing a '_new' bytecode.
-      return true;
-    }
-  }
-  if (C->is_compiling_clinit_for(field_holder)) {
-    return true; // access in the context of static initializer
-  }
-  return false;
-}
-
-
 void Parse::do_field_access(bool is_get, bool is_field) {
   bool will_link;
   ciField* field = iter().get_field(will_link);
@@ -88,15 +55,6 @@
     return;
   }
 
-  if (!is_field && !field_holder->is_initialized()) {
-    if (!static_field_ok_in_clinit(field, method())) {
-      uncommon_trap(Deoptimization::Reason_uninitialized,
-                    Deoptimization::Action_reinterpret,
-                    NULL, "!static_field_ok_in_clinit");
-      return;
-    }
-  }
-
   // Deoptimize on putfield writes to call site target field.
   if (!is_get && field->is_call_site_target()) {
     uncommon_trap(Deoptimization::Reason_unhandled,
@@ -105,6 +63,11 @@
     return;
   }
 
+  if (C->needs_clinit_barrier(field, method())) {
+    clinit_barrier(field_holder, method());
+    if (stopped())  return;
+  }
+
   assert(field->will_link(method(), bc()), "getfield: typeflow responsibility");
 
   // Note:  We do not check for an unloaded field type here any more.