< prev index next >

src/hotspot/share/runtime/reflection.cpp

Print this page

        

@@ -701,22 +701,43 @@
         }
       }
     }
   }
 
+  // package access
   if (!access.is_private() && is_same_class_package(current_class, field_class)) {
     return true;
   }
 
+  // private access between different classes needs a nestmate check, but
+  // not for anonymous classes - so check host_class
+  if (access.is_private() && host_class == current_class) {
+    // FIXME: can we actually get here with non-instance classes?
+    if (current_class->is_instance_klass() && field_class->is_instance_klass() ) {
+      InstanceKlass* cur_ik = const_cast<InstanceKlass*>(InstanceKlass::cast(current_class));
+      InstanceKlass* field_ik = const_cast<InstanceKlass*>(InstanceKlass::cast(field_class));
+      // Nestmate access checks may require resolution and validation of the nest-host
+      Thread* THREAD = Thread::current();
+      bool access = cur_ik->has_nestmate_access_to(field_ik, THREAD);
+      if (HAS_PENDING_EXCEPTION) {
+        return false;
+      }
+      if (access) {
+        guarantee(resolved_class->is_subclass_of(field_class), "must be!");
+        return true;
+      }
+    }
+  }
+
   // Allow all accesses from jdk/internal/reflect/MagicAccessorImpl subclasses to
   // succeed trivially.
   if (current_class->is_subclass_of(SystemDictionary::reflect_MagicAccessorImpl_klass())) {
     return true;
   }
 
-  return can_relax_access_check_for(
-    current_class, field_class, classloader_only);
+  // Check for special relaxations
+  return can_relax_access_check_for(current_class, field_class, classloader_only);
 }
 
 bool Reflection::is_same_class_package(const Klass* class1, const Klass* class2) {
   return InstanceKlass::cast(class1)->is_same_class_package(class2);
 }
< prev index next >