0N/A/*
1879N/A * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
0N/A * published by the Free Software Foundation.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
1472N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1472N/A * or visit www.oracle.com if you need additional information or have any
1472N/A * questions.
0N/A *
0N/A */
0N/A
1879N/A#include "precompiled.hpp"
1879N/A#include "classfile/systemDictionary.hpp"
1879N/A#include "classfile/vmSymbols.hpp"
1879N/A#include "memory/resourceArea.hpp"
1879N/A#include "memory/universe.inline.hpp"
1879N/A#include "oops/instanceKlass.hpp"
3767N/A#include "oops/fieldStreams.hpp"
1879N/A#include "runtime/fieldDescriptor.hpp"
1879N/A#include "runtime/handles.inline.hpp"
1879N/A#include "runtime/signature.hpp"
0N/A
0N/A
0N/Aoop fieldDescriptor::loader() const {
0N/A return instanceKlass::cast(_cp->pool_holder())->class_loader();
0N/A}
0N/A
3767N/ASymbol* fieldDescriptor::generic_signature() const {
3842N/A if (!has_generic_signature()) {
3842N/A return NULL;
3842N/A }
3842N/A
3767N/A int idx = 0;
3767N/A instanceKlass* ik = instanceKlass::cast(field_holder());
3767N/A for (AllFieldStream fs(ik); !fs.done(); fs.next()) {
3767N/A if (idx == _index) {
3767N/A return fs.generic_signature();
3767N/A } else {
3767N/A idx ++;
3767N/A }
3767N/A }
3767N/A assert(false, "should never happen");
3767N/A return NULL;
3767N/A}
3767N/A
0N/AtypeArrayOop fieldDescriptor::annotations() const {
0N/A instanceKlass* ik = instanceKlass::cast(field_holder());
0N/A objArrayOop md = ik->fields_annotations();
0N/A if (md == NULL)
0N/A return NULL;
2771N/A return typeArrayOop(md->obj_at(index()));
0N/A}
0N/A
0N/AconstantTag fieldDescriptor::initial_value_tag() const {
2771N/A return constants()->tag_at(initial_value_index());
0N/A}
0N/A
0N/Ajint fieldDescriptor::int_initial_value() const {
2771N/A return constants()->int_at(initial_value_index());
0N/A}
0N/A
0N/Ajlong fieldDescriptor::long_initial_value() const {
2771N/A return constants()->long_at(initial_value_index());
0N/A}
0N/A
0N/Ajfloat fieldDescriptor::float_initial_value() const {
2771N/A return constants()->float_at(initial_value_index());
0N/A}
0N/A
0N/Ajdouble fieldDescriptor::double_initial_value() const {
2771N/A return constants()->double_at(initial_value_index());
0N/A}
0N/A
0N/Aoop fieldDescriptor::string_initial_value(TRAPS) const {
2771N/A return constants()->string_at(initial_value_index(), CHECK_0);
0N/A}
0N/A
0N/Avoid fieldDescriptor::initialize(klassOop k, int index) {
0N/A instanceKlass* ik = instanceKlass::cast(k);
0N/A _cp = ik->constants();
2771N/A FieldInfo* f = ik->field(index);
2771N/A assert(!f->is_internal(), "regular Java fields only");
0N/A
2771N/A _access_flags = accessFlags_from(f->access_flags());
2771N/A guarantee(f->name_index() != 0 && f->signature_index() != 0, "bad constant pool index for fieldDescriptor");
0N/A _index = index;
0N/A}
0N/A
0N/A#ifndef PRODUCT
0N/A
0N/Avoid fieldDescriptor::print_on(outputStream* st) const {
2771N/A access_flags().print_on(st);
2771N/A name()->print_value_on(st);
0N/A st->print(" ");
2771N/A signature()->print_value_on(st);
0N/A st->print(" @%d ", offset());
0N/A if (WizardMode && has_initial_value()) {
0N/A st->print("(initval ");
0N/A constantTag t = initial_value_tag();
0N/A if (t.is_int()) {
0N/A st->print("int %d)", int_initial_value());
0N/A } else if (t.is_long()){
0N/A st->print_jlong(long_initial_value());
0N/A } else if (t.is_float()){
0N/A st->print("float %f)", float_initial_value());
0N/A } else if (t.is_double()){
0N/A st->print("double %lf)", double_initial_value());
0N/A }
0N/A }
0N/A}
0N/A
0N/Avoid fieldDescriptor::print_on_for(outputStream* st, oop obj) {
0N/A print_on(st);
0N/A BasicType ft = field_type();
665N/A jint as_int = 0;
0N/A switch (ft) {
0N/A case T_BYTE:
0N/A as_int = (jint)obj->byte_field(offset());
0N/A st->print(" %d", obj->byte_field(offset()));
0N/A break;
0N/A case T_CHAR:
665N/A as_int = (jint)obj->char_field(offset());
0N/A {
0N/A jchar c = obj->char_field(offset());
0N/A as_int = c;
0N/A st->print(" %c %d", isprint(c) ? c : ' ', c);
0N/A }
0N/A break;
0N/A case T_DOUBLE:
0N/A st->print(" %lf", obj->double_field(offset()));
0N/A break;
0N/A case T_FLOAT:
0N/A as_int = obj->int_field(offset());
0N/A st->print(" %f", obj->float_field(offset()));
0N/A break;
0N/A case T_INT:
665N/A as_int = obj->int_field(offset());
0N/A st->print(" %d", obj->int_field(offset()));
0N/A break;
0N/A case T_LONG:
0N/A st->print(" ");
0N/A st->print_jlong(obj->long_field(offset()));
0N/A break;
0N/A case T_SHORT:
0N/A as_int = obj->short_field(offset());
0N/A st->print(" %d", obj->short_field(offset()));
0N/A break;
0N/A case T_BOOLEAN:
0N/A as_int = obj->bool_field(offset());
0N/A st->print(" %s", obj->bool_field(offset()) ? "true" : "false");
0N/A break;
0N/A case T_ARRAY:
0N/A st->print(" ");
665N/A NOT_LP64(as_int = obj->int_field(offset()));
0N/A obj->obj_field(offset())->print_value_on(st);
0N/A break;
0N/A case T_OBJECT:
0N/A st->print(" ");
665N/A NOT_LP64(as_int = obj->int_field(offset()));
0N/A obj->obj_field(offset())->print_value_on(st);
0N/A break;
0N/A default:
0N/A ShouldNotReachHere();
0N/A break;
0N/A }
0N/A // Print a hint as to the underlying integer representation. This can be wrong for
0N/A // pointers on an LP64 machine
665N/A if (ft == T_LONG || ft == T_DOUBLE LP64_ONLY(|| !is_java_primitive(ft)) ) {
0N/A st->print(" (%x %x)", obj->int_field(offset()), obj->int_field(offset()+sizeof(jint)));
665N/A } else if (as_int < 0 || as_int > 9) {
0N/A st->print(" (%x)", as_int);
0N/A }
0N/A}
0N/A
0N/A#endif /* PRODUCT */