mirror of
https://github.com/openjdk/jdk7u.git
synced 2025-12-15 14:45:34 -06:00
8199226: Improve field accesses
Reviewed-by: andrew
This commit is contained in:
parent
0ed02c94be
commit
f1e2b7f0a7
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2018, 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
|
||||
@ -582,6 +582,37 @@ void LinkResolver::check_field_accessability(KlassHandle ref_klass,
|
||||
}
|
||||
}
|
||||
|
||||
void LinkResolver::check_field_loader_constraints(KlassHandle ref_klass,
|
||||
KlassHandle sel_klass,
|
||||
Symbol* name,
|
||||
Symbol* sig, TRAPS) {
|
||||
HandleMark hm(THREAD);
|
||||
Handle ref_loader (THREAD, instanceKlass::cast(ref_klass())->class_loader());
|
||||
Handle sel_loader (THREAD, instanceKlass::cast(sel_klass())->class_loader());
|
||||
{
|
||||
ResourceMark rm(THREAD);
|
||||
char* failed_type_name =
|
||||
SystemDictionary::check_signature_loaders(sig, ref_loader, sel_loader,
|
||||
false, CHECK);
|
||||
if (failed_type_name != NULL) {
|
||||
const char* msg = "loader constraint violation: when resolving field"
|
||||
" \"%s\" the class loader (instance of %s) of the referring class, "
|
||||
"%s, and the class loader (instance of %s) for the field's resolved "
|
||||
"type, %s, have different Class objects for that type";
|
||||
char* field_name = name->as_C_string();
|
||||
const char* loader1 = SystemDictionary::loader_name(ref_loader());
|
||||
char* sel = instanceKlass::cast(sel_klass())->name()->as_C_string();
|
||||
const char* loader2 = SystemDictionary::loader_name(sel_loader());
|
||||
size_t buflen = strlen(msg) + strlen(field_name) + strlen(loader1) +
|
||||
strlen(sel) + strlen(loader2) + strlen(failed_type_name);
|
||||
char* buf = NEW_RESOURCE_ARRAY_IN_THREAD(THREAD, char, buflen);
|
||||
jio_snprintf(buf, buflen, msg, field_name, loader1, sel, loader2,
|
||||
failed_type_name);
|
||||
THROW_MSG(vmSymbols::java_lang_LinkageError(), buf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LinkResolver::resolve_field(FieldAccessInfo& result, constantPoolHandle pool, int index, Bytecodes::Code byte, bool check_only, TRAPS) {
|
||||
resolve_field(result, pool, index, byte, check_only, true, CHECK);
|
||||
}
|
||||
@ -644,37 +675,7 @@ void LinkResolver::resolve_field(FieldAccessInfo& result, constantPoolHandle poo
|
||||
if (is_static && !check_only) {
|
||||
sel_klass->initialize(CHECK);
|
||||
}
|
||||
|
||||
{
|
||||
HandleMark hm(THREAD);
|
||||
Handle ref_loader (THREAD, instanceKlass::cast(ref_klass())->class_loader());
|
||||
Handle sel_loader (THREAD, instanceKlass::cast(sel_klass())->class_loader());
|
||||
Symbol* signature_ref = pool->signature_ref_at(index);
|
||||
{
|
||||
ResourceMark rm(THREAD);
|
||||
char* failed_type_name =
|
||||
SystemDictionary::check_signature_loaders(signature_ref,
|
||||
ref_loader, sel_loader,
|
||||
false,
|
||||
CHECK);
|
||||
if (failed_type_name != NULL) {
|
||||
const char* msg = "loader constraint violation: when resolving field"
|
||||
" \"%s\" the class loader (instance of %s) of the referring class, "
|
||||
"%s, and the class loader (instance of %s) for the field's resolved "
|
||||
"type, %s, have different Class objects for that type";
|
||||
char* field_name = field->as_C_string();
|
||||
const char* loader1 = SystemDictionary::loader_name(ref_loader());
|
||||
char* sel = instanceKlass::cast(sel_klass())->name()->as_C_string();
|
||||
const char* loader2 = SystemDictionary::loader_name(sel_loader());
|
||||
size_t buflen = strlen(msg) + strlen(field_name) + strlen(loader1) +
|
||||
strlen(sel) + strlen(loader2) + strlen(failed_type_name);
|
||||
char* buf = NEW_RESOURCE_ARRAY_IN_THREAD(THREAD, char, buflen);
|
||||
jio_snprintf(buf, buflen, msg, field_name, loader1, sel, loader2,
|
||||
failed_type_name);
|
||||
THROW_MSG(vmSymbols::java_lang_LinkageError(), buf);
|
||||
}
|
||||
}
|
||||
}
|
||||
LinkResolver::check_field_loader_constraints(ref_klass, sel_klass, field, sig, CHECK);
|
||||
|
||||
// return information. note that the klass is set to the actual klass containing the
|
||||
// field, otherwise access of static fields in superclasses will not work.
|
||||
|
||||
@ -188,6 +188,7 @@ class LinkResolver: AllStatic {
|
||||
static void resolve_invokehandle (CallInfo& result, constantPoolHandle pool, int index, TRAPS);
|
||||
|
||||
static void resolve_invoke (CallInfo& result, Handle recv, constantPoolHandle pool, int index, Bytecodes::Code byte, TRAPS);
|
||||
static void check_field_loader_constraints(KlassHandle ref_klass, KlassHandle sel_klass, Symbol* name, Symbol* sig, TRAPS);
|
||||
};
|
||||
|
||||
#endif // SHARE_VM_INTERPRETER_LINKRESOLVER_HPP
|
||||
|
||||
@ -767,6 +767,12 @@ Handle MethodHandles::resolve_MemberName(Handle mname, KlassHandle caller, TRAPS
|
||||
KlassHandle sel_klass(THREAD, instanceKlass::cast(defc())->find_field(name, type, &fd));
|
||||
// check if field exists; i.e., if a klass containing the field def has been selected
|
||||
if (sel_klass.is_null()) return empty; // should not happen
|
||||
if (sel_klass() != caller() && caller.not_null()) {
|
||||
LinkResolver::check_field_loader_constraints(caller, sel_klass, name, type, THREAD);
|
||||
if (HAS_PENDING_EXCEPTION) {
|
||||
return empty;
|
||||
}
|
||||
}
|
||||
oop type = field_signature_type_or_null(fd.signature());
|
||||
oop name = field_name_or_null(fd.name());
|
||||
bool is_setter = (ref_kind_is_valid(ref_kind) && ref_kind_is_setter(ref_kind));
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user