< prev index next >
src/share/vm/interpreter/linkResolver.cpp
Print this page
*** 1,7 ****
/*
! * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
--- 1,7 ----
/*
! * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*** 246,255 ****
--- 246,256 ----
_resolved_klass = KlassHandle(THREAD, result);
// Get name, signature, and static klass
_name = pool->name_ref_at(index);
_signature = pool->signature_ref_at(index);
+ _tag = pool->tag_ref_at(index);
_current_klass = KlassHandle(THREAD, pool->pool_holder());
// Coming from the constant pool always checks access
_check_access = true;
}
*** 682,691 ****
--- 683,701 ----
jio_snprintf(buf, sizeof(buf), "Found interface %s, but class was expected",
resolved_klass()->external_name());
THROW_MSG_NULL(vmSymbols::java_lang_IncompatibleClassChangeError(), buf);
}
+ // check tag at call is method
+ if (!link_info.tag().is_invalid() && !link_info.tag().is_method()) {
+ ResourceMark rm(THREAD);
+ char buf[200];
+ jio_snprintf(buf, sizeof(buf), "Resolving to non regular method %s", link_info.method_string());
+ THROW_MSG_NULL(vmSymbols::java_lang_IncompatibleClassChangeError(), buf);
+ }
+
+
// 2. lookup method in resolved klass and its super klasses
methodHandle resolved_method = lookup_method_in_klasses(link_info, true, false, CHECK_NULL);
if (resolved_method.is_null() && !resolved_klass->is_array_klass()) { // not found in the class hierarchy
// 3. lookup method in all the interfaces implemented by the resolved klass
*** 771,780 ****
--- 781,798 ----
char buf[200];
jio_snprintf(buf, sizeof(buf), "Found class %s, but interface was expected", resolved_klass()->external_name());
THROW_MSG_NULL(vmSymbols::java_lang_IncompatibleClassChangeError(), buf);
}
+ // check tag at call is an interface method
+ if (!link_info.tag().is_invalid() && !link_info.tag().is_interface_method()) {
+ ResourceMark rm(THREAD);
+ char buf[200];
+ jio_snprintf(buf, sizeof(buf), "Resolving to non interface method %s", link_info.method_string());
+ THROW_MSG_NULL(vmSymbols::java_lang_IncompatibleClassChangeError(), buf);
+ }
+
// lookup method in this interface or its super, java.lang.Object
// JDK8: also look for static methods
methodHandle resolved_method = lookup_method_in_klasses(link_info, false, true, CHECK_NULL);
if (resolved_method.is_null() && !resolved_klass->is_array_klass()) {
*** 948,958 ****
// Initialize klass (this should only happen if everything is ok)
if (initialize_class && resolved_klass->should_be_initialized()) {
resolved_klass->initialize(CHECK);
// Use updated LinkInfo (to reresolve with resolved_klass as method_holder?)
LinkInfo new_info(resolved_klass, link_info.name(), link_info.signature(),
! link_info.current_klass(), link_info.check_access());
resolved_method = linktime_resolve_static_method(new_info, CHECK);
}
assert(save_resolved_method == resolved_method(), "does this change?");
// setup result
--- 966,977 ----
// Initialize klass (this should only happen if everything is ok)
if (initialize_class && resolved_klass->should_be_initialized()) {
resolved_klass->initialize(CHECK);
// Use updated LinkInfo (to reresolve with resolved_klass as method_holder?)
LinkInfo new_info(resolved_klass, link_info.name(), link_info.signature(),
! link_info.current_klass(),
! link_info.check_access() ? LinkInfo::needs_access_check : LinkInfo::skip_access_check);
resolved_method = linktime_resolve_static_method(new_info, CHECK);
}
assert(save_resolved_method == resolved_method(), "does this change?");
// setup result
*** 1489,1499 ****
const methodHandle& attached_method,
Bytecodes::Code byte, TRAPS) {
KlassHandle defc = attached_method->method_holder();
Symbol* name = attached_method->name();
Symbol* type = attached_method->signature();
! LinkInfo link_info(defc, name, type, KlassHandle(), /*check_access=*/false);
switch(byte) {
case Bytecodes::_invokevirtual:
resolve_virtual_call(result, recv, recv->klass(), link_info,
/*check_null_and_abstract=*/true, CHECK);
break;
--- 1508,1518 ----
const methodHandle& attached_method,
Bytecodes::Code byte, TRAPS) {
KlassHandle defc = attached_method->method_holder();
Symbol* name = attached_method->name();
Symbol* type = attached_method->signature();
! LinkInfo link_info(defc, name, type, KlassHandle(), LinkInfo::skip_access_check);
switch(byte) {
case Bytecodes::_invokevirtual:
resolve_virtual_call(result, recv, recv->klass(), link_info,
/*check_null_and_abstract=*/true, CHECK);
break;
< prev index next >