nmethod.cpp revision 1202
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * This code is free software; you can redistribute it and/or modify it
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * under the terms of the GNU General Public License version 2 only, as
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * published by the Free Software Foundation.
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * This code is distributed in the hope that it will be useful, but WITHOUT
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * version 2 for more details (a copy is included in the LICENSE file that
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * accompanied this code).
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * You should have received a copy of the GNU General Public License version
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * 2 along with this work; if not, write to the Free Software Foundation,
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * CA 95054 USA or visit www.sun.com if you need additional information or
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter * have any questions.
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suter# include "incls/_precompiled.incl"
a5b9f8fb834b1b2208e59a2fa76714bd91a5f147violette# include "incls/_nmethod.cpp.incl"
a5b9f8fb834b1b2208e59a2fa76714bd91a5f147violette// Only bother with this argument setup if dtrace is available
5b3741e0620fd2baaa974cecc2c2d953bb7d4fbbkenneth_suterHS_DTRACE_PROBE_DECL8(hotspot, compiled__method__load,
a5b9f8fb834b1b2208e59a2fa76714bd91a5f147violette const char*, int, const char*, int, const char*, int, void*, size_t);
27f8adec83293fb8bd3bfa37175322b0ee3bb933jvergaraHS_DTRACE_PROBE_DECL6(hotspot, compiled__method__unload,
a5b9f8fb834b1b2208e59a2fa76714bd91a5f147violette char*, int, char*, int, char*, int);
if (m != NULL) { \
if (is_native_method()) return false;
if (is_native_method()) return false;
#ifndef PRODUCT
struct nmethod_stats_struct {
int nmethod_count;
int total_size;
int relocation_size;
int code_size;
int stub_size;
int consts_size;
int scopes_data_size;
int scopes_pcs_size;
int dependencies_size;
int handler_table_size;
int nul_chk_table_size;
int oops_size;
void print_nmethod_stats() {
if (nmethod_count == 0) return;
int native_nmethod_count;
int native_total_size;
int native_code_size;
int native_oops_size;
void print_native_nmethod_stats() {
if (native_nmethod_count == 0) return;
void print_pc_stats() {
/ pc_desc_queries);
_count = 0;
return NULL;
for (int i=0; i<count(); i++) {
return handler_at(i);
return NULL;
return ec;
return NULL;
if (!approximate)
for (int i = 0; i < cache_size; i++)
return res;
for (int i = 0; i < cache_size; i++) {
return res;
return NULL;
for (int i = 0; i < cache_size; i++) {
return nsize;
delete curr;
return ret_val;
return NULL;
*(jint*)this = 0;
code_size() +
stub_size() +
consts_size() +
scopes_data_size() +
scopes_pcs_size() +
return NULL;
int vep_offset,
int frame_complete,
int frame_size,
oop_maps);
return nm;
#ifdef HAVE_DTRACE_H
int vep_offset,
int trap_offset,
int frame_complete,
int frame_size) {
return nm;
int compile_id,
int entry_bci,
int orig_pc_offset,
int comp_level
int nmethod_size =
return nm;
int nmethod_size,
int frame_size,
_scavenge_root_state = 0;
_exception_offset = 0;
_deoptimize_offset = 0;
_orig_pc_offset = 0;
#ifdef HAVE_DTRACE_H
_trap_offset = 0;
_lock_count = 0;
print();
if (PrintNativeNMethods) {
print_code();
if (PrintRelocations) {
#ifdef HAVE_DTRACE_H
int nmethod_size,
int frame_size)
_scavenge_root_state = 0;
_exception_offset = 0;
_deoptimize_offset = 0;
_orig_pc_offset = 0;
_lock_count = 0;
print();
if (PrintNMethods) {
print_code();
if (PrintRelocations) {
int nmethod_size,
int compile_id,
int entry_bci,
int orig_pc_offset,
int frame_size,
int comp_level
_scavenge_root_state = 0;
#ifdef HAVE_DTRACE_H
_trap_offset = 0;
_consts_offset = instructions_offset() + code_buffer->total_offset_of(code_buffer->consts()->start());
_lock_count = 0;
if (printnmethods || PrintDebugInfo || PrintRelocations || PrintDependencies || PrintExceptionHandlers) {
#ifdef TIERED
bool do_nl = false;
compile_id(),
#ifdef TIERED
if (is_osr_method())
print();
if (printmethod) {
print_code();
print_pcs();
if (PrintDebugInfo) {
print_scopes();
if (PrintRelocations) {
if (PrintDependencies) {
if (PrintExceptionHandlers) {
if (is_zombie()) {
if (!is_in_use()) {
// Tell if a non-entrant method can be converted to a zombie (i.e., there is no activations on the stack)
if (m == NULL) return;
// There is a benign race here. See comments in methodDataOop.hpp.
if (is_osr_method()) {
if (is_in_use()) {
if (LogCompilation) {
if (is_zombie()) {
if (is_osr_method()) {
if (TraceCreateZombies) {
tty->print_cr("nmethod <" INTPTR_FORMAT "> code made %s", this, (state == not_entrant) ? "not entrant" : "zombie");
!unload_reported()) {
#ifndef PRODUCT
assert(is_marked_for_reclamation() || (is_osr_method() && is_unloaded()), "must be marked for reclamation");
if (PrintMethodFlushing) {
tty->print_cr("*flushing nmethod %3d/" INTPTR_FORMAT ". Live blobs:" UINT32_FORMAT "/Free CodeCache:" SIZE_FORMAT "Kb",
delete ec;
if (on_scavenge_root_list()) {
if (is_speculatively_disconnected()) {
if (!has_flushed_dependencies()) {
if (is_not_entrant()) {
// to no longer be true. See jvmtiExport.hpp for details.
if (a_class_was_redefined) {
unloading_occurred = true;
if (unloading_occurred) {
#ifndef PRODUCT
if (is_not_entrant()) {
if (!do_strong_roots_only) {
f->do_oop(p);
bool _detected_scavenge_root;
_detected_scavenge_root = true;
#ifndef PRODUCT
(*p)->print();
return NULL;
#ifdef ASSERT
for (int i = 0; i < count; i++) {
#ifdef ASSERT
res = p;
return res;
return res;
#define assert_LU_OK \
return upper;
return NULL;
bool found_check = false;
found_check = true;
NOT_DEBUG(break);
found_check = true;
NOT_DEBUG(break);
return found_check;
if (is_zombie()) {
#ifdef ASSERT
if (cont_offset == 0) {
print();
print_code();
print_pcs();
void nmethod_init() {
return ret;
if (!has_method_handle_invokes()) return false;
bool _ok;
if (_ok) {
_ok = false;
if(is_native_method() )
if (nm != this) {
if (! p->verify(this)) {
#ifndef PRODUCT
bool _ok;
if (_ok) {
_ok = false;
(*p)->print();
if (!on_scavenge_root_list()) {
if (is_compiled_by_c1()) {
} else if (is_compiled_by_c2()) {
if (WizardMode) {
(address)this,
size());
relocation_size());
code_begin(),
code_end(),
code_size());
stub_begin(),
stub_end(),
stub_size());
consts_begin(),
consts_end(),
consts_size());
if (scopes_data_size () > 0) tty->print_cr(" scopes data [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
scopes_data_size());
scopes_pcs_size());
if (dependencies_size () > 0) tty->print_cr(" dependencies [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
if (handler_table_size() > 0) tty->print_cr(" handler table [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
if (nul_chk_table_size() > 0) tty->print_cr(" nul chk table [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
oops_begin(),
oops_end(),
oops_size());
ResourceMark m;
#ifndef PRODUCT
if (UseRelocIndex) {
if (index_size > 0) {
ip[0],
p->print(this);
bool have_one = false;
have_one = true;
return NULL;
if (m.not_null()) {
int sig_index = 0;
if (!m->is_static())
int sig_index = 0;
bool did_old_sp = false;
bool at_old_sp = false;
if (at_this)
if (at_this) {
bool did_name = false;
did_name = true;
if (!did_name)
if (at_old_sp) {
did_old_sp = true;
if (!did_old_sp) {
switch (bc) {
if (cont_offset != 0) {
st->print("; implicit exception: dispatches to " INTPTR_FORMAT, instructions_begin() + cont_offset);
#ifndef PRODUCT