diff --git a/src/hotspot/share/oops/klassVtable.cpp b/src/hotspot/share/oops/klassVtable.cpp index 20a8063771d97..8d13310cdc7a0 100644 --- a/src/hotspot/share/oops/klassVtable.cpp +++ b/src/hotspot/share/oops/klassVtable.cpp @@ -1180,38 +1180,42 @@ void klassItable::check_constraints(GrowableArray* supers, TRAPS) { Method* interface_method = supers->at(i); // method overridden if (target != nullptr && interface_method != nullptr) { - InstanceKlass* method_holder = target->method_holder(); - InstanceKlass* interf = interface_method->method_holder(); - HandleMark hm(THREAD); - Handle method_holder_loader(THREAD, method_holder->class_loader()); - Handle interface_loader(THREAD, interf->class_loader()); - - if (method_holder_loader() != interface_loader()) { - ResourceMark rm(THREAD); - Symbol* failed_type_symbol = - SystemDictionary::check_signature_loaders(target->signature(), - _klass, - method_holder_loader, - interface_loader, - true); - if (failed_type_symbol != nullptr) { - stringStream ss; - ss.print("loader constraint violation in interface itable" - " initialization for class %s: when selecting method '", - _klass->external_name()); - interface_method->print_external_name(&ss), - ss.print("' the class loader %s for super interface %s, and the class" - " loader %s of the selected method's %s, %s have" - " different Class objects for the type %s used in the signature (%s; %s)", - interf->class_loader_data()->loader_name_and_id(), - interf->external_name(), - method_holder->class_loader_data()->loader_name_and_id(), - method_holder->external_kind(), - method_holder->external_name(), - failed_type_symbol->as_klass_external_name(), - interf->class_in_module_of_loader(false, true), - method_holder->class_in_module_of_loader(false, true)); - THROW_MSG(vmSymbols::java_lang_LinkageError(), ss.as_string()); + // Do not check loader constraints for overpass methods because overpass + // methods are created by the jvm to throw exceptions. + if (!target->is_overpass()) { + InstanceKlass* method_holder = target->method_holder(); + InstanceKlass* interf = interface_method->method_holder(); + HandleMark hm(THREAD); + Handle method_holder_loader(THREAD, method_holder->class_loader()); + Handle interface_loader(THREAD, interf->class_loader()); + + if (method_holder_loader() != interface_loader()) { + ResourceMark rm(THREAD); + Symbol* failed_type_symbol = + SystemDictionary::check_signature_loaders(target->signature(), + _klass, + method_holder_loader, + interface_loader, + true); + if (failed_type_symbol != nullptr) { + stringStream ss; + ss.print("loader constraint violation in interface itable" + " initialization for class %s: when selecting method '", + _klass->external_name()); + interface_method->print_external_name(&ss), + ss.print("' the class loader %s for super interface %s, and the class" + " loader %s of the selected method's %s, %s have" + " different Class objects for the type %s used in the signature (%s; %s)", + interf->class_loader_data()->loader_name_and_id(), + interf->external_name(), + method_holder->class_loader_data()->loader_name_and_id(), + method_holder->external_kind(), + method_holder->external_name(), + failed_type_symbol->as_klass_external_name(), + interf->class_in_module_of_loader(false, true), + method_holder->class_in_module_of_loader(false, true)); + THROW_MSG(vmSymbols::java_lang_LinkageError(), ss.as_string()); + } } } } @@ -1333,11 +1337,9 @@ void klassItable::initialize_itable_for_interface(int method_table_offset, Insta target = LinkResolver::lookup_instance_method_in_klasses(_klass, m->name(), m->signature(), Klass::PrivateLookupMode::skip); } - if (target == nullptr || !target->is_public() || target->is_abstract() || target->is_overpass()) { - assert(target == nullptr || !target->is_overpass() || target->is_public(), - "Non-public overpass method!"); + if (target == nullptr || !target->is_public() || target->is_abstract()) { // Entry does not resolve. Leave it empty for AbstractMethodError or other error. - if (!(target == nullptr) && !target->is_public()) { + if (target != nullptr && !target->is_public()) { // Stuff an IllegalAccessError throwing method in there instead. itableOffsetEntry::method_entry(_klass, method_table_offset)[m->itable_index()]. initialize(_klass, Universe::throw_illegal_access_error()); diff --git a/test/hotspot/jtreg/vmTestbase/vm/runtime/defmeth/ConflictingDefaultsTest.java b/test/hotspot/jtreg/vmTestbase/vm/runtime/defmeth/ConflictingDefaultsTest.java index c5de16d583e11..6421797298062 100644 --- a/test/hotspot/jtreg/vmTestbase/vm/runtime/defmeth/ConflictingDefaultsTest.java +++ b/test/hotspot/jtreg/vmTestbase/vm/runtime/defmeth/ConflictingDefaultsTest.java @@ -82,6 +82,8 @@ public static void main(String[] args) { * class C implements I, J {} * * TEST: C c = new C(); c.m() ==> ICCE + * TEST: I c = new C(); c.m() ==> ICCE + * TEST: J c = new C(); c.m() ==> ICCE */ public void testConflict(TestBuilder b) { Interface I = b.intf("I") @@ -95,7 +97,13 @@ public void testConflict(TestBuilder b) { ConcreteClass C = b.clazz("C").implement(I,J).build(); b.test().callSite(C, C, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) + .done() + .test().callSite(I, C, "m","()I") + .throwsExact(IncompatibleClassChangeError.class) + .done() + .test().callSite(J, C, "m","()I") + .throwsExact(IncompatibleClassChangeError.class) .done(); } @@ -145,7 +153,7 @@ public void testReabstract(TestBuilder b) { ConcreteClass C = b.clazz("C").implement(J).build(); b.test().callSite(C, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done(); } @@ -177,16 +185,16 @@ public void testReabstract2(TestBuilder b) { .build(); b.test().callSite(C, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done() .test().callSite(J, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done() .test().callSite(I, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done() .test().callSite(D, D, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done(); } @@ -218,7 +226,7 @@ public void testReabstractConflictingDefaults(TestBuilder b) { ConcreteClass C = b.clazz("C").extend(A).implement(K).build(); b.test().callSite(A, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done(); } @@ -259,13 +267,13 @@ public void testReabstractConflictingDefaultsInvokeInterface(TestBuilder b) { ConcreteClass D = b.clazz("D").extend(C).implement(L).build(); b.test().callSite(I, A, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) .done() .test().callSite(K, C, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done() .test().callSite(L, D, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done(); } @@ -307,10 +315,10 @@ public void testReabstractConflictingDefaultsSuper(TestBuilder b) { .build(); b.test().callSite(I, A, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) .done() .test().callSite(L, D, "m","()I") - .throws_(AbstractMethodError.class) + .throwsExact(AbstractMethodError.class) .done(); } @@ -370,22 +378,22 @@ public void testReabstractResolveMethod00705m2(TestBuilder b) { } b.test().callSite(A, C, "m", "()I") - .throws_(expectedError2) + .throwsExact(expectedError2) .done() .test().callSite(C, C, "m", "()I") - .throws_(expectedError2) + .throwsExact(expectedError2) .done() .test().callSite(J, C, "m", "()I") - .throws_(expectedError1) + .throwsExact(expectedError1) .done() .test().callSite(I, C, "m", "()I") - .throws_(expectedError1) + .throwsExact(expectedError1) .done() .test().callSite(C, C, "test_Cmethod_ISMR", "()V") - .throws_(expectedError2) + .throwsExact(expectedError2) .done() .test().callSite(A, C, "test_Amethod_ISIMR", "()V") - .throws_(expectedError2) + .throwsExact(expectedError2) .done(); } @@ -486,13 +494,13 @@ public void testMixedArity1(TestBuilder b) { .test() .callSite(I, C, "m","(I)I") .params(0) - .throws_(NoSuchMethodError.class) + .throwsExact(NoSuchMethodError.class) .done() // J j = new C(); ... .test() .callSite(J, C, "m","()I") - .throws_(NoSuchMethodError.class) + .throwsExact(NoSuchMethodError.class) .done() .test() .callSite(J, C, "m","(I)I") @@ -539,19 +547,19 @@ public void testMixedArity2(TestBuilder b) { // I i = new C(); ... b.test() .callSite(I, C, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) .done() // J j = new C(); ... .test() .callSite(J, C, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) .done() // C c = new C(); ... .test() .callSite(C, C, "m","()I") - .throws_(IncompatibleClassChangeError.class) + .throwsExact(IncompatibleClassChangeError.class) .done() .test() .callSite(C, C, "m","(I)I")