comparison src/share/vm/asm/codeBuffer.cpp @ 6725:da91efe96a93

6964458: Reimplement class meta-data storage to use native memory Summary: Remove PermGen, allocate meta-data in metaspace linked to class loaders, rewrite GC walking, rewrite and rename metadata to be C++ classes Reviewed-by: jmasa, stefank, never, coleenp, kvn, brutisso, mgerdin, dholmes, jrose, twisti, roland Contributed-by: jmasa <jon.masamitsu@oracle.com>, stefank <stefan.karlsson@oracle.com>, mgerdin <mikael.gerdin@oracle.com>, never <tom.rodriguez@oracle.com>
author coleenp
date Sat, 01 Sep 2012 13:25:18 -0400
parents d2a62e0f25eb
children b31471cdc53e
comparison
equal deleted inserted replaced
6724:36d1d483d5d6 6725:da91efe96a93
1 /* 1 /*
2 * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved. 2 * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 * 4 *
5 * This code is free software; you can redistribute it and/or modify it 5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as 6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. 7 * published by the Free Software Foundation.
23 */ 23 */
24 24
25 #include "precompiled.hpp" 25 #include "precompiled.hpp"
26 #include "asm/codeBuffer.hpp" 26 #include "asm/codeBuffer.hpp"
27 #include "compiler/disassembler.hpp" 27 #include "compiler/disassembler.hpp"
28 #include "memory/gcLocker.hpp"
29 #include "oops/methodData.hpp"
30 #include "oops/oop.inline.hpp"
28 #include "utilities/copy.hpp" 31 #include "utilities/copy.hpp"
29 #include "utilities/xmlstream.hpp" 32 #include "utilities/xmlstream.hpp"
30 33
31 // The structure of a CodeSection: 34 // The structure of a CodeSection:
32 // 35 //
140 #endif 143 #endif
141 } 144 }
142 145
143 void CodeBuffer::initialize_oop_recorder(OopRecorder* r) { 146 void CodeBuffer::initialize_oop_recorder(OopRecorder* r) {
144 assert(_oop_recorder == &_default_oop_recorder && _default_oop_recorder.is_unused(), "do this once"); 147 assert(_oop_recorder == &_default_oop_recorder && _default_oop_recorder.is_unused(), "do this once");
145 DEBUG_ONLY(_default_oop_recorder.oop_size()); // force unused OR to be frozen 148 DEBUG_ONLY(_default_oop_recorder.freeze()); // force unused OR to be frozen
146 _oop_recorder = r; 149 _oop_recorder = r;
147 } 150 }
148 151
149 void CodeBuffer::initialize_section_size(CodeSection* cs, csize_t size) { 152 void CodeBuffer::initialize_section_size(CodeSection* cs, csize_t size) {
150 assert(cs != &_insts, "insts is the memory provider, not the consumer"); 153 assert(cs != &_insts, "insts is the memory provider, not the consumer");
487 // Done calculating sections; did it come out to the right end? 490 // Done calculating sections; did it come out to the right end?
488 assert(buf_offset == total_content_size(), "sanity"); 491 assert(buf_offset == total_content_size(), "sanity");
489 dest->verify_section_allocation(); 492 dest->verify_section_allocation();
490 } 493 }
491 494
495 void CodeBuffer::finalize_oop_references(methodHandle mh) {
496 No_Safepoint_Verifier nsv;
497
498 GrowableArray<oop> oops;
499
500 // Make sure that immediate metadata records something in the OopRecorder
501 for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
502 // pull code out of each section
503 CodeSection* cs = code_section(n);
504 if (cs->is_empty()) continue; // skip trivial section
505 RelocIterator iter(cs);
506 while (iter.next()) {
507 if (iter.type() == relocInfo::metadata_type) {
508 metadata_Relocation* md = iter.metadata_reloc();
509 if (md->metadata_is_immediate()) {
510 Metadata* m = md->metadata_value();
511 if (oop_recorder()->is_real(m)) {
512 oop o = NULL;
513 if (m->is_methodData()) {
514 m = ((MethodData*)m)->method();
515 }
516 if (m->is_method()) {
517 m = ((Method*)m)->method_holder();
518 }
519 if (m->is_klass()) {
520 o = ((Klass*)m)->class_loader();
521 } else {
522 // XXX This will currently occur for MDO which don't
523 // have a backpointer. This has to be fixed later.
524 m->print();
525 ShouldNotReachHere();
526 }
527 if (o != NULL && oops.find(o) == -1) {
528 oops.append(o);
529 }
530 }
531 }
532 }
533 }
534 }
535
536 if (!oop_recorder()->is_unused()) {
537 for (int i = 0; i < oop_recorder()->metadata_count(); i++) {
538 Metadata* m = oop_recorder()->metadata_at(i);
539 if (oop_recorder()->is_real(m)) {
540 oop o = NULL;
541 if (m->is_methodData()) {
542 m = ((MethodData*)m)->method();
543 }
544 if (m->is_method()) {
545 m = ((Method*)m)->method_holder();
546 }
547 if (m->is_klass()) {
548 o = ((Klass*)m)->class_loader();
549 } else {
550 m->print();
551 ShouldNotReachHere();
552 }
553 if (o != NULL && oops.find(o) == -1) {
554 oops.append(o);
555 }
556 }
557 }
558
559 }
560
561 // Add the class loader of Method* for the nmethod itself
562 oop cl = mh->method_holder()->class_loader();
563 if (cl != NULL) {
564 oops.append(cl);
565 }
566
567 // Add any oops that we've found
568 Thread* thread = Thread::current();
569 for (int i = 0; i < oops.length(); i++) {
570 oop_recorder()->find_index((jobject)thread->handle_area()->allocate_handle(oops.at(i)));
571 }
572 }
573
574
575
492 csize_t CodeBuffer::total_offset_of(CodeSection* cs) const { 576 csize_t CodeBuffer::total_offset_of(CodeSection* cs) const {
493 csize_t size_so_far = 0; 577 csize_t size_so_far = 0;
494 for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) { 578 for (int n = (int) SECT_FIRST; n < (int) SECT_LIMIT; n++) {
495 const CodeSection* cur_cs = code_section(n); 579 const CodeSection* cur_cs = code_section(n);
496 if (!cur_cs->is_empty()) { 580 if (!cur_cs->is_empty()) {