提交 4fd3d50f 编写于 作者: T twisti

6961697: move nmethod constants section before instruction section

Summary: This is a preparation for 6961690.
Reviewed-by: kvn, never
上级 0f9d7325
...@@ -143,13 +143,6 @@ void CodeBuffer::initialize_oop_recorder(OopRecorder* r) { ...@@ -143,13 +143,6 @@ void CodeBuffer::initialize_oop_recorder(OopRecorder* r) {
void CodeBuffer::initialize_section_size(CodeSection* cs, csize_t size) { void CodeBuffer::initialize_section_size(CodeSection* cs, csize_t size) {
assert(cs != &_insts, "insts is the memory provider, not the consumer"); assert(cs != &_insts, "insts is the memory provider, not the consumer");
#ifdef ASSERT
for (int n = (int)SECT_INSTS+1; n < (int)SECT_LIMIT; n++) {
CodeSection* prevCS = code_section(n);
if (prevCS == cs) break;
assert(!prevCS->is_allocated(), "section allocation must be in reverse order");
}
#endif
csize_t slop = CodeSection::end_slop(); // margin between sections csize_t slop = CodeSection::end_slop(); // margin between sections
int align = cs->alignment(); int align = cs->alignment();
assert(is_power_of_2(align), "sanity"); assert(is_power_of_2(align), "sanity");
...@@ -199,13 +192,13 @@ void CodeBuffer::set_blob(BufferBlob* blob) { ...@@ -199,13 +192,13 @@ void CodeBuffer::set_blob(BufferBlob* blob) {
_total_start = start; _total_start = start;
_total_size = end - start; _total_size = end - start;
} else { } else {
#ifdef ASSERT #ifdef ASSERT
// Clean out dangling pointers. // Clean out dangling pointers.
_total_start = badAddress; _total_start = badAddress;
_consts._start = _consts._end = badAddress;
_insts._start = _insts._end = badAddress; _insts._start = _insts._end = badAddress;
_stubs._start = _stubs._end = badAddress; _stubs._start = _stubs._end = badAddress;
_consts._start = _consts._end = badAddress; #endif //ASSERT
#endif //ASSERT
} }
} }
...@@ -221,9 +214,9 @@ const char* CodeBuffer::code_section_name(int n) { ...@@ -221,9 +214,9 @@ const char* CodeBuffer::code_section_name(int n) {
return NULL; return NULL;
#else //PRODUCT #else //PRODUCT
switch (n) { switch (n) {
case SECT_CONSTS: return "consts";
case SECT_INSTS: return "insts"; case SECT_INSTS: return "insts";
case SECT_STUBS: return "stubs"; case SECT_STUBS: return "stubs";
case SECT_CONSTS: return "consts";
default: return NULL; default: return NULL;
} }
#endif //PRODUCT #endif //PRODUCT
...@@ -445,12 +438,11 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const { ...@@ -445,12 +438,11 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const {
const CodeSection* prev_cs = NULL; const CodeSection* prev_cs = NULL;
CodeSection* prev_dest_cs = NULL; CodeSection* prev_dest_cs = NULL;
for (int n = 0; n < (int)SECT_LIMIT; n++) {
for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
// figure compact layout of each section // figure compact layout of each section
const CodeSection* cs = code_section(n); const CodeSection* cs = code_section(n);
address cstart = cs->start(); csize_t csize = cs->size();
address cend = cs->end();
csize_t csize = cend - cstart;
CodeSection* dest_cs = dest->code_section(n); CodeSection* dest_cs = dest->code_section(n);
if (!cs->is_empty()) { if (!cs->is_empty()) {
...@@ -463,7 +455,7 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const { ...@@ -463,7 +455,7 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const {
prev_dest_cs->_limit += padding; prev_dest_cs->_limit += padding;
} }
#ifdef ASSERT #ifdef ASSERT
if (prev_cs != NULL && prev_cs->is_frozen() && n < SECT_CONSTS) { if (prev_cs != NULL && prev_cs->is_frozen() && n < (SECT_LIMIT - 1)) {
// Make sure the ends still match up. // Make sure the ends still match up.
// This is important because a branch in a frozen section // This is important because a branch in a frozen section
// might target code in a following section, via a Label, // might target code in a following section, via a Label,
...@@ -492,22 +484,18 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const { ...@@ -492,22 +484,18 @@ void CodeBuffer::compute_final_layout(CodeBuffer* dest) const {
assert(dest->verify_section_allocation(), "final configuration works"); assert(dest->verify_section_allocation(), "final configuration works");
} }
csize_t CodeBuffer::total_offset_of(address addr) const { csize_t CodeBuffer::total_offset_of(CodeSection* cs) const {
csize_t code_size_so_far = 0; csize_t size_so_far = 0;
for (int n = 0; n < (int)SECT_LIMIT; n++) { for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
const CodeSection* cs = code_section(n); const CodeSection* cur_cs = code_section(n);
if (!cs->is_empty()) { if (!cur_cs->is_empty()) {
code_size_so_far = cs->align_at_start(code_size_so_far); size_so_far = cur_cs->align_at_start(size_so_far);
} }
if (cs->contains2(addr)) { if (cur_cs->index() == cs->index()) {
return code_size_so_far + (addr - cs->start()); return size_so_far;
} }
code_size_so_far += cs->size(); size_so_far += cur_cs->size();
} }
#ifndef PRODUCT
tty->print_cr("Dangling address " PTR_FORMAT " in:", addr);
((CodeBuffer*)this)->print();
#endif
ShouldNotReachHere(); ShouldNotReachHere();
return -1; return -1;
} }
...@@ -533,7 +521,7 @@ csize_t CodeBuffer::copy_relocations_to(CodeBlob* dest) const { ...@@ -533,7 +521,7 @@ csize_t CodeBuffer::copy_relocations_to(CodeBlob* dest) const {
csize_t code_end_so_far = 0; csize_t code_end_so_far = 0;
csize_t code_point_so_far = 0; csize_t code_point_so_far = 0;
for (int n = 0; n < (int)SECT_LIMIT; n++) { for (int n = (int) SECT_FIRST; n < (int)SECT_LIMIT; n++) {
// pull relocs out of each section // pull relocs out of each section
const CodeSection* cs = code_section(n); const CodeSection* cs = code_section(n);
assert(!(cs->is_empty() && cs->locs_count() > 0), "sanity"); assert(!(cs->is_empty() && cs->locs_count() > 0), "sanity");
...@@ -635,11 +623,14 @@ void CodeBuffer::copy_code_to(CodeBlob* dest_blob) { ...@@ -635,11 +623,14 @@ void CodeBuffer::copy_code_to(CodeBlob* dest_blob) {
ICache::invalidate_range(dest_blob->code_begin(), dest_blob->code_size()); ICache::invalidate_range(dest_blob->code_begin(), dest_blob->code_size());
} }
// Move all my code into another code buffer. // Move all my code into another code buffer. Consult applicable
// Consult applicable relocs to repair embedded addresses. // relocs to repair embedded addresses. The layout in the destination
// CodeBuffer is different to the source CodeBuffer: the destination
// CodeBuffer gets the final layout (consts, insts, stubs in order of
// ascending address).
void CodeBuffer::relocate_code_to(CodeBuffer* dest) const { void CodeBuffer::relocate_code_to(CodeBuffer* dest) const {
DEBUG_ONLY(address dest_end = dest->_total_start + dest->_total_size); DEBUG_ONLY(address dest_end = dest->_total_start + dest->_total_size);
for (int n = 0; n < (int)SECT_LIMIT; n++) { for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
// pull code out of each section // pull code out of each section
const CodeSection* cs = code_section(n); const CodeSection* cs = code_section(n);
if (cs->is_empty()) continue; // skip trivial section if (cs->is_empty()) continue; // skip trivial section
...@@ -681,20 +672,19 @@ csize_t CodeBuffer::figure_expanded_capacities(CodeSection* which_cs, ...@@ -681,20 +672,19 @@ csize_t CodeBuffer::figure_expanded_capacities(CodeSection* which_cs,
csize_t* new_capacity) { csize_t* new_capacity) {
csize_t new_total_cap = 0; csize_t new_total_cap = 0;
int prev_n = -1; for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
for (int n = 0; n < (int)SECT_LIMIT; n++) {
const CodeSection* sect = code_section(n); const CodeSection* sect = code_section(n);
if (!sect->is_empty()) { if (!sect->is_empty()) {
// Compute initial padding; assign it to the previous non-empty guy. // Compute initial padding; assign it to the previous section,
// Cf. compute_final_layout. // even if it's empty (e.g. consts section can be empty).
// Cf. compute_final_layout
csize_t padding = sect->align_at_start(new_total_cap) - new_total_cap; csize_t padding = sect->align_at_start(new_total_cap) - new_total_cap;
if (padding != 0) { if (padding != 0) {
new_total_cap += padding; new_total_cap += padding;
assert(prev_n >= 0, "sanity"); assert(n - 1 >= SECT_FIRST, "sanity");
new_capacity[prev_n] += padding; new_capacity[n - 1] += padding;
} }
prev_n = n;
} }
csize_t exp = sect->size(); // 100% increase csize_t exp = sect->size(); // 100% increase
...@@ -774,11 +764,11 @@ void CodeBuffer::expand(CodeSection* which_cs, csize_t amount) { ...@@ -774,11 +764,11 @@ void CodeBuffer::expand(CodeSection* which_cs, csize_t amount) {
this->_before_expand = bxp; this->_before_expand = bxp;
// Give each section its required (expanded) capacity. // Give each section its required (expanded) capacity.
for (int n = (int)SECT_LIMIT-1; n >= SECT_INSTS; n--) { for (int n = (int)SECT_LIMIT-1; n >= SECT_FIRST; n--) {
CodeSection* cb_sect = cb.code_section(n); CodeSection* cb_sect = cb.code_section(n);
CodeSection* this_sect = code_section(n); CodeSection* this_sect = code_section(n);
if (new_capacity[n] == 0) continue; // already nulled out if (new_capacity[n] == 0) continue; // already nulled out
if (n > SECT_INSTS) { if (n != SECT_INSTS) {
cb.initialize_section_size(cb_sect, new_capacity[n]); cb.initialize_section_size(cb_sect, new_capacity[n]);
} }
assert(cb_sect->capacity() >= new_capacity[n], "big enough"); assert(cb_sect->capacity() >= new_capacity[n], "big enough");
...@@ -844,16 +834,21 @@ bool CodeBuffer::verify_section_allocation() { ...@@ -844,16 +834,21 @@ bool CodeBuffer::verify_section_allocation() {
assert(tstart >= _blob->content_begin(), "sanity"); assert(tstart >= _blob->content_begin(), "sanity");
assert(tend <= _blob->content_end(), "sanity"); assert(tend <= _blob->content_end(), "sanity");
} }
address tcheck = tstart; // advancing pointer to verify disjointness // Verify disjointness.
for (int n = 0; n < (int)SECT_LIMIT; n++) { for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
CodeSection* sect = code_section(n); CodeSection* sect = code_section(n);
if (!sect->is_allocated()) continue; if (!sect->is_allocated() || sect->is_empty()) continue;
assert(sect->start() >= tcheck, "sanity"); assert((intptr_t)sect->start() % sect->alignment() == 0
tcheck = sect->start();
assert((intptr_t)tcheck % sect->alignment() == 0
|| sect->is_empty() || _blob == NULL, || sect->is_empty() || _blob == NULL,
"start is aligned"); "start is aligned");
assert(sect->end() >= tcheck, "sanity"); for (int m = (int) SECT_FIRST; m < (int) SECT_LIMIT; m++) {
CodeSection* other = code_section(m);
if (!other->is_allocated() || other == sect) continue;
assert(!other->contains(sect->start() ), "sanity");
// limit is an exclusive address and can be the start of another
// section.
assert(!other->contains(sect->limit() - 1), "sanity");
}
assert(sect->end() <= tend, "sanity"); assert(sect->end() <= tend, "sanity");
} }
return true; return true;
......
...@@ -289,10 +289,12 @@ class CodeBuffer: public StackObj { ...@@ -289,10 +289,12 @@ class CodeBuffer: public StackObj {
public: public:
typedef int csize_t; // code size type; would be size_t except for history typedef int csize_t; // code size type; would be size_t except for history
enum { enum {
// Here is the list of all possible sections, in order of ascending address. // Here is the list of all possible sections. The order reflects
// the final layout.
SECT_FIRST = 0,
SECT_CONSTS = SECT_FIRST, // Non-instruction data: Floats, jump tables, etc.
SECT_INSTS, // Executable instructions. SECT_INSTS, // Executable instructions.
SECT_STUBS, // Outbound trampolines for supporting call sites. SECT_STUBS, // Outbound trampolines for supporting call sites.
SECT_CONSTS, // Non-instruction data: Floats, jump tables, etc.
SECT_LIMIT, SECT_NONE = -1 SECT_LIMIT, SECT_NONE = -1
}; };
...@@ -304,9 +306,9 @@ class CodeBuffer: public StackObj { ...@@ -304,9 +306,9 @@ class CodeBuffer: public StackObj {
const char* _name; const char* _name;
CodeSection _consts; // constants, jump tables
CodeSection _insts; // instructions (the main section) CodeSection _insts; // instructions (the main section)
CodeSection _stubs; // stubs (call site support), deopt, exception handling CodeSection _stubs; // stubs (call site support), deopt, exception handling
CodeSection _consts; // constants, jump tables
CodeBuffer* _before_expand; // dead buffer, from before the last expansion CodeBuffer* _before_expand; // dead buffer, from before the last expansion
...@@ -334,9 +336,9 @@ class CodeBuffer: public StackObj { ...@@ -334,9 +336,9 @@ class CodeBuffer: public StackObj {
} }
void initialize(address code_start, csize_t code_size) { void initialize(address code_start, csize_t code_size) {
_consts.initialize_outer(this, SECT_CONSTS);
_insts.initialize_outer(this, SECT_INSTS); _insts.initialize_outer(this, SECT_INSTS);
_stubs.initialize_outer(this, SECT_STUBS); _stubs.initialize_outer(this, SECT_STUBS);
_consts.initialize_outer(this, SECT_CONSTS);
_total_start = code_start; _total_start = code_start;
_total_size = code_size; _total_size = code_size;
// Initialize the main section: // Initialize the main section:
...@@ -414,16 +416,16 @@ class CodeBuffer: public StackObj { ...@@ -414,16 +416,16 @@ class CodeBuffer: public StackObj {
// construction. // construction.
void initialize(csize_t code_size, csize_t locs_size); void initialize(csize_t code_size, csize_t locs_size);
CodeSection* consts() { return &_consts; }
CodeSection* insts() { return &_insts; } CodeSection* insts() { return &_insts; }
CodeSection* stubs() { return &_stubs; } CodeSection* stubs() { return &_stubs; }
CodeSection* consts() { return &_consts; }
// present sections in order; return NULL at end; insts is #0, etc. // present sections in order; return NULL at end; consts is #0, etc.
CodeSection* code_section(int n) { CodeSection* code_section(int n) {
// This makes the slightly questionable but portable assumption that // This makes the slightly questionable but portable assumption
// the various members (_insts, _stubs, etc.) are adjacent in the // that the various members (_consts, _insts, _stubs, etc.) are
// layout of CodeBuffer. // adjacent in the layout of CodeBuffer.
CodeSection* cs = &_insts + n; CodeSection* cs = &_consts + n;
assert(cs->index() == n || !cs->is_allocated(), "sanity"); assert(cs->index() == n || !cs->is_allocated(), "sanity");
return cs; return cs;
} }
...@@ -484,9 +486,9 @@ class CodeBuffer: public StackObj { ...@@ -484,9 +486,9 @@ class CodeBuffer: public StackObj {
// CodeBlob). // CodeBlob).
csize_t total_content_size() const; csize_t total_content_size() const;
// combined offset (relative to start of insts) of given address, // Combined offset (relative to start of first section) of given
// as eventually found in the final CodeBlob // section, as eventually found in the final CodeBlob.
csize_t total_offset_of(address addr) const; csize_t total_offset_of(CodeSection* cs) const;
// allocated size of all relocation data, including index, rounded up // allocated size of all relocation data, including index, rounded up
csize_t total_relocation_size() const; csize_t total_relocation_size() const;
......
...@@ -92,7 +92,7 @@ CodeBlob::CodeBlob( ...@@ -92,7 +92,7 @@ CodeBlob::CodeBlob(
_header_size = header_size; _header_size = header_size;
_relocation_size = round_to(cb->total_relocation_size(), oopSize); _relocation_size = round_to(cb->total_relocation_size(), oopSize);
_content_offset = align_code_offset(header_size + _relocation_size); _content_offset = align_code_offset(header_size + _relocation_size);
_code_offset = _content_offset + cb->total_offset_of(cb->insts()->start()); _code_offset = _content_offset + cb->total_offset_of(cb->insts());
_data_offset = _content_offset + round_to(cb->total_content_size(), oopSize); _data_offset = _content_offset + round_to(cb->total_content_size(), oopSize);
assert(_data_offset <= size, "codeBlob is too small"); assert(_data_offset <= size, "codeBlob is too small");
......
...@@ -87,9 +87,9 @@ struct nmethod_stats_struct { ...@@ -87,9 +87,9 @@ struct nmethod_stats_struct {
int nmethod_count; int nmethod_count;
int total_size; int total_size;
int relocation_size; int relocation_size;
int consts_size;
int insts_size; int insts_size;
int stub_size; int stub_size;
int consts_size;
int scopes_data_size; int scopes_data_size;
int scopes_pcs_size; int scopes_pcs_size;
int dependencies_size; int dependencies_size;
...@@ -101,9 +101,9 @@ struct nmethod_stats_struct { ...@@ -101,9 +101,9 @@ struct nmethod_stats_struct {
nmethod_count += 1; nmethod_count += 1;
total_size += nm->size(); total_size += nm->size();
relocation_size += nm->relocation_size(); relocation_size += nm->relocation_size();
consts_size += nm->consts_size();
insts_size += nm->insts_size(); insts_size += nm->insts_size();
stub_size += nm->stub_size(); stub_size += nm->stub_size();
consts_size += nm->consts_size();
oops_size += nm->oops_size(); oops_size += nm->oops_size();
scopes_data_size += nm->scopes_data_size(); scopes_data_size += nm->scopes_data_size();
scopes_pcs_size += nm->scopes_pcs_size(); scopes_pcs_size += nm->scopes_pcs_size();
...@@ -116,9 +116,9 @@ struct nmethod_stats_struct { ...@@ -116,9 +116,9 @@ struct nmethod_stats_struct {
tty->print_cr("Statistics for %d bytecoded nmethods:", nmethod_count); tty->print_cr("Statistics for %d bytecoded nmethods:", nmethod_count);
if (total_size != 0) tty->print_cr(" total in heap = %d", total_size); if (total_size != 0) tty->print_cr(" total in heap = %d", total_size);
if (relocation_size != 0) tty->print_cr(" relocation = %d", relocation_size); if (relocation_size != 0) tty->print_cr(" relocation = %d", relocation_size);
if (consts_size != 0) tty->print_cr(" constants = %d", consts_size);
if (insts_size != 0) tty->print_cr(" main code = %d", insts_size); if (insts_size != 0) tty->print_cr(" main code = %d", insts_size);
if (stub_size != 0) tty->print_cr(" stub code = %d", stub_size); if (stub_size != 0) tty->print_cr(" stub code = %d", stub_size);
if (consts_size != 0) tty->print_cr(" constants = %d", consts_size);
if (oops_size != 0) tty->print_cr(" oops = %d", oops_size); if (oops_size != 0) tty->print_cr(" oops = %d", oops_size);
if (scopes_data_size != 0) tty->print_cr(" scopes data = %d", scopes_data_size); if (scopes_data_size != 0) tty->print_cr(" scopes data = %d", scopes_data_size);
if (scopes_pcs_size != 0) tty->print_cr(" scopes pcs = %d", scopes_pcs_size); if (scopes_pcs_size != 0) tty->print_cr(" scopes pcs = %d", scopes_pcs_size);
...@@ -404,9 +404,9 @@ void nmethod::add_handler_for_exception_and_pc(Handle exception, address pc, add ...@@ -404,9 +404,9 @@ void nmethod::add_handler_for_exception_and_pc(Handle exception, address pc, add
int nmethod::total_size() const { int nmethod::total_size() const {
return return
consts_size() +
insts_size() + insts_size() +
stub_size() + stub_size() +
consts_size() +
scopes_data_size() + scopes_data_size() +
scopes_pcs_size() + scopes_pcs_size() +
handler_table_size() + handler_table_size() +
...@@ -789,13 +789,17 @@ nmethod::nmethod( ...@@ -789,13 +789,17 @@ nmethod::nmethod(
_orig_pc_offset = orig_pc_offset; _orig_pc_offset = orig_pc_offset;
// Section offsets // Section offsets
_consts_offset = content_offset() + code_buffer->total_offset_of(code_buffer->consts()->start()); _consts_offset = content_offset() + code_buffer->total_offset_of(code_buffer->consts());
_stub_offset = content_offset() + code_buffer->total_offset_of(code_buffer->stubs()->start()); _stub_offset = content_offset() + code_buffer->total_offset_of(code_buffer->stubs());
// Exception handler and deopt handler are in the stub section // Exception handler and deopt handler are in the stub section
_exception_offset = _stub_offset + offsets->value(CodeOffsets::Exceptions); _exception_offset = _stub_offset + offsets->value(CodeOffsets::Exceptions);
_deoptimize_offset = _stub_offset + offsets->value(CodeOffsets::Deopt); _deoptimize_offset = _stub_offset + offsets->value(CodeOffsets::Deopt);
if (has_method_handle_invokes()) {
_deoptimize_mh_offset = _stub_offset + offsets->value(CodeOffsets::DeoptMH); _deoptimize_mh_offset = _stub_offset + offsets->value(CodeOffsets::DeoptMH);
} else {
_deoptimize_mh_offset = -1;
}
if (offsets->value(CodeOffsets::UnwindHandler) != -1) { if (offsets->value(CodeOffsets::UnwindHandler) != -1) {
_unwind_handler_offset = code_offset() + offsets->value(CodeOffsets::UnwindHandler); _unwind_handler_offset = code_offset() + offsets->value(CodeOffsets::UnwindHandler);
} else { } else {
...@@ -885,9 +889,9 @@ void nmethod::log_new_nmethod() const { ...@@ -885,9 +889,9 @@ void nmethod::log_new_nmethod() const {
xtty->print(" address='" INTPTR_FORMAT "'", (intptr_t) this); xtty->print(" address='" INTPTR_FORMAT "'", (intptr_t) this);
LOG_OFFSET(xtty, relocation); LOG_OFFSET(xtty, relocation);
LOG_OFFSET(xtty, consts);
LOG_OFFSET(xtty, insts); LOG_OFFSET(xtty, insts);
LOG_OFFSET(xtty, stub); LOG_OFFSET(xtty, stub);
LOG_OFFSET(xtty, consts);
LOG_OFFSET(xtty, scopes_data); LOG_OFFSET(xtty, scopes_data);
LOG_OFFSET(xtty, scopes_pcs); LOG_OFFSET(xtty, scopes_pcs);
LOG_OFFSET(xtty, dependencies); LOG_OFFSET(xtty, dependencies);
...@@ -2336,6 +2340,10 @@ void nmethod::print() const { ...@@ -2336,6 +2340,10 @@ void nmethod::print() const {
relocation_begin(), relocation_begin(),
relocation_end(), relocation_end(),
relocation_size()); relocation_size());
if (consts_size () > 0) tty->print_cr(" constants [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
consts_begin(),
consts_end(),
consts_size());
if (insts_size () > 0) tty->print_cr(" main code [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d", if (insts_size () > 0) tty->print_cr(" main code [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
insts_begin(), insts_begin(),
insts_end(), insts_end(),
...@@ -2344,10 +2352,6 @@ void nmethod::print() const { ...@@ -2344,10 +2352,6 @@ void nmethod::print() const {
stub_begin(), stub_begin(),
stub_end(), stub_end(),
stub_size()); stub_size());
if (consts_size () > 0) tty->print_cr(" constants [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
consts_begin(),
consts_end(),
consts_size());
if (oops_size () > 0) tty->print_cr(" oops [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d", if (oops_size () > 0) tty->print_cr(" oops [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
oops_begin(), oops_begin(),
oops_end(), oops_end(),
...@@ -2372,10 +2376,6 @@ void nmethod::print() const { ...@@ -2372,10 +2376,6 @@ void nmethod::print() const {
nul_chk_table_begin(), nul_chk_table_begin(),
nul_chk_table_end(), nul_chk_table_end(),
nul_chk_table_size()); nul_chk_table_size());
if (oops_size () > 0) tty->print_cr(" oops [" INTPTR_FORMAT "," INTPTR_FORMAT "] = %d",
oops_begin(),
oops_end(),
oops_size());
} }
void nmethod::print_code() { void nmethod::print_code() {
......
...@@ -143,8 +143,8 @@ class nmethod : public CodeBlob { ...@@ -143,8 +143,8 @@ class nmethod : public CodeBlob {
#ifdef HAVE_DTRACE_H #ifdef HAVE_DTRACE_H
int _trap_offset; int _trap_offset;
#endif // def HAVE_DTRACE_H #endif // def HAVE_DTRACE_H
int _stub_offset;
int _consts_offset; int _consts_offset;
int _stub_offset;
int _oops_offset; // offset to where embedded oop table begins (inside data) int _oops_offset; // offset to where embedded oop table begins (inside data)
int _scopes_data_offset; int _scopes_data_offset;
int _scopes_pcs_offset; int _scopes_pcs_offset;
...@@ -336,16 +336,16 @@ class nmethod : public CodeBlob { ...@@ -336,16 +336,16 @@ class nmethod : public CodeBlob {
bool is_compiled_by_shark() const; bool is_compiled_by_shark() const;
// boundaries for different parts // boundaries for different parts
address insts_begin () const { return code_begin(); } address consts_begin () const { return header_begin() + _consts_offset ; }
address consts_end () const { return header_begin() + code_offset() ; }
address insts_begin () const { return header_begin() + code_offset() ; }
address insts_end () const { return header_begin() + _stub_offset ; } address insts_end () const { return header_begin() + _stub_offset ; }
address stub_begin () const { return header_begin() + _stub_offset ; }
address stub_end () const { return header_begin() + _oops_offset ; }
address exception_begin () const { return header_begin() + _exception_offset ; } address exception_begin () const { return header_begin() + _exception_offset ; }
address deopt_handler_begin () const { return header_begin() + _deoptimize_offset ; } address deopt_handler_begin () const { return header_begin() + _deoptimize_offset ; }
address deopt_mh_handler_begin() const { return header_begin() + _deoptimize_mh_offset ; } address deopt_mh_handler_begin() const { return header_begin() + _deoptimize_mh_offset ; }
address unwind_handler_begin () const { return _unwind_handler_offset != -1 ? (header_begin() + _unwind_handler_offset) : NULL; } address unwind_handler_begin () const { return _unwind_handler_offset != -1 ? (header_begin() + _unwind_handler_offset) : NULL; }
address stub_begin () const { return header_begin() + _stub_offset ; }
address stub_end () const { return header_begin() + _consts_offset ; }
address consts_begin () const { return header_begin() + _consts_offset ; }
address consts_end () const { return header_begin() + _oops_offset ; }
oop* oops_begin () const { return (oop*) (header_begin() + _oops_offset) ; } oop* oops_begin () const { return (oop*) (header_begin() + _oops_offset) ; }
oop* oops_end () const { return (oop*) (header_begin() + _scopes_data_offset) ; } oop* oops_end () const { return (oop*) (header_begin() + _scopes_data_offset) ; }
...@@ -361,9 +361,9 @@ class nmethod : public CodeBlob { ...@@ -361,9 +361,9 @@ class nmethod : public CodeBlob {
address nul_chk_table_end () const { return header_begin() + _nmethod_end_offset ; } address nul_chk_table_end () const { return header_begin() + _nmethod_end_offset ; }
// Sizes // Sizes
int consts_size () const { return consts_end () - consts_begin (); }
int insts_size () const { return insts_end () - insts_begin (); } int insts_size () const { return insts_end () - insts_begin (); }
int stub_size () const { return stub_end () - stub_begin (); } int stub_size () const { return stub_end () - stub_begin (); }
int consts_size () const { return consts_end () - consts_begin (); }
int oops_size () const { return (address) oops_end () - (address) oops_begin (); } int oops_size () const { return (address) oops_end () - (address) oops_begin (); }
int scopes_data_size () const { return scopes_data_end () - scopes_data_begin (); } int scopes_data_size () const { return scopes_data_end () - scopes_data_begin (); }
int scopes_pcs_size () const { return (intptr_t) scopes_pcs_end () - (intptr_t) scopes_pcs_begin (); } int scopes_pcs_size () const { return (intptr_t) scopes_pcs_end () - (intptr_t) scopes_pcs_begin (); }
...@@ -374,9 +374,9 @@ class nmethod : public CodeBlob { ...@@ -374,9 +374,9 @@ class nmethod : public CodeBlob {
int total_size () const; int total_size () const;
// Containment // Containment
bool consts_contains (address addr) const { return consts_begin () <= addr && addr < consts_end (); }
bool insts_contains (address addr) const { return insts_begin () <= addr && addr < insts_end (); } bool insts_contains (address addr) const { return insts_begin () <= addr && addr < insts_end (); }
bool stub_contains (address addr) const { return stub_begin () <= addr && addr < stub_end (); } bool stub_contains (address addr) const { return stub_begin () <= addr && addr < stub_end (); }
bool consts_contains (address addr) const { return consts_begin () <= addr && addr < consts_end (); }
bool oops_contains (oop* addr) const { return oops_begin () <= addr && addr < oops_end (); } bool oops_contains (oop* addr) const { return oops_begin () <= addr && addr < oops_end (); }
bool scopes_data_contains (address addr) const { return scopes_data_begin () <= addr && addr < scopes_data_end (); } bool scopes_data_contains (address addr) const { return scopes_data_begin () <= addr && addr < scopes_data_end (); }
bool scopes_pcs_contains (PcDesc* addr) const { return scopes_pcs_begin () <= addr && addr < scopes_pcs_end (); } bool scopes_pcs_contains (PcDesc* addr) const { return scopes_pcs_begin () <= addr && addr < scopes_pcs_end (); }
......
...@@ -128,7 +128,16 @@ void RelocIterator::initialize(nmethod* nm, address begin, address limit) { ...@@ -128,7 +128,16 @@ void RelocIterator::initialize(nmethod* nm, address begin, address limit) {
_code = nm; _code = nm;
_current = nm->relocation_begin() - 1; _current = nm->relocation_begin() - 1;
_end = nm->relocation_end(); _end = nm->relocation_end();
_addr = (address) nm->code_begin(); _addr = nm->content_begin();
// Initialize code sections.
_section_start[CodeBuffer::SECT_CONSTS] = nm->consts_begin();
_section_start[CodeBuffer::SECT_INSTS ] = nm->insts_begin() ;
_section_start[CodeBuffer::SECT_STUBS ] = nm->stub_begin() ;
_section_end [CodeBuffer::SECT_CONSTS] = nm->consts_end() ;
_section_end [CodeBuffer::SECT_INSTS ] = nm->insts_end() ;
_section_end [CodeBuffer::SECT_STUBS ] = nm->stub_end() ;
assert(!has_current(), "just checking"); assert(!has_current(), "just checking");
assert(begin == NULL || begin >= nm->code_begin(), "in bounds"); assert(begin == NULL || begin >= nm->code_begin(), "in bounds");
...@@ -146,9 +155,11 @@ RelocIterator::RelocIterator(CodeSection* cs, address begin, address limit) { ...@@ -146,9 +155,11 @@ RelocIterator::RelocIterator(CodeSection* cs, address begin, address limit) {
_code = NULL; // Not cb->blob(); _code = NULL; // Not cb->blob();
CodeBuffer* cb = cs->outer(); CodeBuffer* cb = cs->outer();
assert((int)SECT_LIMIT == CodeBuffer::SECT_LIMIT, "my copy must be equal"); assert((int) SECT_LIMIT == CodeBuffer::SECT_LIMIT, "my copy must be equal");
for (int n = 0; n < (int)SECT_LIMIT; n++) { for (int n = (int) CodeBuffer::SECT_FIRST; n < (int) CodeBuffer::SECT_LIMIT; n++) {
_section_start[n] = cb->code_section(n)->start(); CodeSection* cs = cb->code_section(n);
_section_start[n] = cs->start();
_section_end [n] = cs->end();
} }
assert(!has_current(), "just checking"); assert(!has_current(), "just checking");
...@@ -166,6 +177,12 @@ struct RelocIndexEntry { ...@@ -166,6 +177,12 @@ struct RelocIndexEntry {
}; };
bool RelocIterator::addr_in_const() const {
const int n = CodeBuffer::SECT_CONSTS;
return section_start(n) <= addr() && addr() < section_end(n);
}
static inline int num_cards(int code_size) { static inline int num_cards(int code_size) {
return (code_size-1) / indexCardSize; return (code_size-1) / indexCardSize;
} }
...@@ -360,31 +377,12 @@ void RelocIterator::advance_over_prefix() { ...@@ -360,31 +377,12 @@ void RelocIterator::advance_over_prefix() {
} }
address RelocIterator::compute_section_start(int n) const { void RelocIterator::initialize_misc() {
// This routine not only computes a section start, but also set_has_current(false);
// memoizes it for later. for (int i = (int) CodeBuffer::SECT_FIRST; i < (int) CodeBuffer::SECT_LIMIT; i++) {
#define CACHE ((RelocIterator*)this)->_section_start[n] _section_start[i] = NULL; // these will be lazily computed, if needed
CodeBlob* cb = code(); _section_end [i] = NULL;
guarantee(cb != NULL, "must have a code blob");
if (n == CodeBuffer::SECT_INSTS)
return CACHE = cb->code_begin();
assert(cb->is_nmethod(), "only nmethods have these sections");
nmethod* nm = (nmethod*) cb;
address res = NULL;
switch (n) {
case CodeBuffer::SECT_STUBS:
res = nm->stub_begin();
break;
case CodeBuffer::SECT_CONSTS:
res = nm->consts_begin();
break;
default:
ShouldNotReachHere();
} }
assert(nm->contains(res) || res == nm->code_end(), "tame pointer");
CACHE = res;
return res;
#undef CACHE
} }
......
/* /*
* Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -502,8 +502,7 @@ class RelocationHolder VALUE_OBJ_CLASS_SPEC { ...@@ -502,8 +502,7 @@ class RelocationHolder VALUE_OBJ_CLASS_SPEC {
// } // }
class RelocIterator : public StackObj { class RelocIterator : public StackObj {
enum { SECT_CONSTS = 2, enum { SECT_LIMIT = 3 }; // must be equal to CodeBuffer::SECT_LIMIT, checked in ctor
SECT_LIMIT = 3 }; // must be equal to CodeBuffer::SECT_LIMIT
friend class Relocation; friend class Relocation;
friend class relocInfo; // for change_reloc_info_for_address only friend class relocInfo; // for change_reloc_info_for_address only
typedef relocInfo::relocType relocType; typedef relocInfo::relocType relocType;
...@@ -521,6 +520,7 @@ class RelocIterator : public StackObj { ...@@ -521,6 +520,7 @@ class RelocIterator : public StackObj {
// Base addresses needed to compute targets of section_word_type relocs. // Base addresses needed to compute targets of section_word_type relocs.
address _section_start[SECT_LIMIT]; address _section_start[SECT_LIMIT];
address _section_end [SECT_LIMIT];
void set_has_current(bool b) { void set_has_current(bool b) {
_datalen = !b ? -1 : 0; _datalen = !b ? -1 : 0;
...@@ -540,14 +540,7 @@ class RelocIterator : public StackObj { ...@@ -540,14 +540,7 @@ class RelocIterator : public StackObj {
void advance_over_prefix(); // helper method void advance_over_prefix(); // helper method
void initialize_misc() { void initialize_misc();
set_has_current(false);
for (int i = 0; i < SECT_LIMIT; i++) {
_section_start[i] = NULL; // these will be lazily computed, if needed
}
}
address compute_section_start(int n) const; // out-of-line helper
void initialize(nmethod* nm, address begin, address limit); void initialize(nmethod* nm, address begin, address limit);
...@@ -598,11 +591,15 @@ class RelocIterator : public StackObj { ...@@ -598,11 +591,15 @@ class RelocIterator : public StackObj {
bool has_current() const { return _datalen >= 0; } bool has_current() const { return _datalen >= 0; }
void set_addr(address addr) { _addr = addr; } void set_addr(address addr) { _addr = addr; }
bool addr_in_const() const { return addr() >= section_start(SECT_CONSTS); } bool addr_in_const() const;
address section_start(int n) const { address section_start(int n) const {
address res = _section_start[n]; assert(_section_start[n], "must be initialized");
return (res != NULL) ? res : compute_section_start(n); return _section_start[n];
}
address section_end(int n) const {
assert(_section_end[n], "must be initialized");
return _section_end[n];
} }
// The address points to the affected displacement part of the instruction. // The address points to the affected displacement part of the instruction.
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册