src/share/vm/oops/klassVtable.cpp

Print this page


   1 /*
   2  * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   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
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *


 628       if (unchecked_method_at(index) == old_method) {
 629         put_method_at(new_method, index);
 630 
 631         if (RC_TRACE_IN_RANGE(0x00100000, 0x00400000)) {
 632           if (!(*trace_name_printed)) {
 633             // RC_TRACE_MESG macro has an embedded ResourceMark
 634             RC_TRACE_MESG(("adjust: name=%s",
 635                            Klass::cast(old_method->method_holder())->external_name()));
 636             *trace_name_printed = true;
 637           }
 638           // RC_TRACE macro has an embedded ResourceMark
 639           RC_TRACE(0x00100000, ("vtable method update: %s(%s)",
 640                                 new_method->name()->as_C_string(),
 641                                 new_method->signature()->as_C_string()));
 642         }
 643       }
 644     }
 645   }
 646 }
 647 




























 648 // CDS/RedefineClasses support - clear vtables so they can be reinitialized
 649 void klassVtable::clear_vtable() {
 650   for (int i = 0; i < _length; i++) table()[i].clear();
 651 }
 652 
 653 bool klassVtable::is_initialized() {
 654   return _length == 0 || table()[0].method() != NULL;
 655 }
 656 
 657 
 658 // Garbage collection
 659 void klassVtable::oop_follow_contents() {
 660   int len = length();
 661   for (int i = 0; i < len; i++) {
 662     MarkSweep::mark_and_push(adr_method_at(i));
 663   }
 664 }
 665 
 666 #ifndef SERIALGC
 667 void klassVtable::oop_follow_contents(ParCompactionManager* cm) {


 977     // The itable can describe more than one interface and the same
 978     // method signature can be specified by more than one interface.
 979     // This means we have to do an exhaustive search to find all the
 980     // old_method references.
 981     for (int i = 0; i < _size_method_table; i++) {
 982       if (ime->method() == old_method) {
 983         ime->initialize(new_method);
 984 
 985         if (RC_TRACE_IN_RANGE(0x00100000, 0x00400000)) {
 986           if (!(*trace_name_printed)) {
 987             // RC_TRACE_MESG macro has an embedded ResourceMark
 988             RC_TRACE_MESG(("adjust: name=%s",
 989               Klass::cast(old_method->method_holder())->external_name()));
 990             *trace_name_printed = true;
 991           }
 992           // RC_TRACE macro has an embedded ResourceMark
 993           RC_TRACE(0x00200000, ("itable method update: %s(%s)",
 994             new_method->name()->as_C_string(),
 995             new_method->signature()->as_C_string()));
 996         }
 997         break;
 998       }
 999       ime++;
1000     }
1001   }
1002 }
1003 












1004 




















1005 // Setup
1006 class InterfaceVisiterClosure : public StackObj {
1007  public:
1008   virtual void doit(klassOop intf, int method_count) = 0;
1009 };
1010 
1011 // Visit all interfaces with at-least one method (excluding <clinit>)
1012 void visit_all_interfaces(objArrayOop transitive_intf, InterfaceVisiterClosure *blk) {
1013   // Handle array argument
1014   for(int i = 0; i < transitive_intf->length(); i++) {
1015     klassOop intf = (klassOop)transitive_intf->obj_at(i);
1016     assert(Klass::cast(intf)->is_interface(), "sanity check");
1017 
1018     // Find no. of methods excluding a <clinit>
1019     int method_count = instanceKlass::cast(intf)->methods()->length();
1020     if (method_count > 0) {
1021       methodOop m = (methodOop)instanceKlass::cast(intf)->methods()->obj_at(0);
1022       assert(m != NULL && m->is_method(), "sanity check");
1023       if (m->name() == vmSymbols::object_initializer_name()) {
1024         method_count--;


1270 int VtableStats::sum_of_vtable_len = 0;
1271 int VtableStats::sum_of_array_vtable_len = 0;
1272 int VtableStats::fixed = 0;
1273 int VtableStats::filler = 0;
1274 int VtableStats::entries = 0;
1275 int VtableStats::array_entries = 0;
1276 
1277 void klassVtable::print_statistics() {
1278   ResourceMark rm;
1279   HandleMark hm;
1280   VtableStats::compute();
1281   tty->print_cr("vtable statistics:");
1282   tty->print_cr("%6d classes (%d instance, %d array)", VtableStats::no_klasses, VtableStats::no_instance_klasses, VtableStats::no_array_klasses);
1283   int total = VtableStats::fixed + VtableStats::filler + VtableStats::entries;
1284   tty->print_cr("%6d bytes fixed overhead (refs + vtable object header)", VtableStats::fixed);
1285   tty->print_cr("%6d bytes filler overhead", VtableStats::filler);
1286   tty->print_cr("%6d bytes for vtable entries (%d for arrays)", VtableStats::entries, VtableStats::array_entries);
1287   tty->print_cr("%6d bytes total", total);
1288 }
1289 
1290 bool klassVtable::check_no_old_entries() {
1291   // Check that there really is no entry
1292   for (int i = 0; i < length(); i++) {
1293     methodOop m = unchecked_method_at(i);
1294     if (m != NULL) {
1295         if (m->is_old()) {
1296             return false;
1297         }
1298     }
1299   }
1300   return true;
1301 }
1302 
1303 void klassVtable::dump_vtable() {
1304   tty->print_cr("vtable dump --");
1305   for (int i = 0; i < length(); i++) {
1306     methodOop m = unchecked_method_at(i);
1307     if (m != NULL) {
1308       tty->print("      (%5d)  ", i);
1309       m->access_flags().print_on(tty);
1310       tty->print(" --  ");
1311       m->print_name(tty);
1312       tty->cr();
1313     }
1314   }
1315 }
1316 
1317 int  klassItable::_total_classes;   // Total no. of classes with itables
1318 long klassItable::_total_size;      // Total no. of bytes used for itables
1319 
1320 void klassItable::print_statistics() {
1321  tty->print_cr("itable statistics:");
1322  tty->print_cr("%6d classes with itables", _total_classes);
1323  tty->print_cr("%6d K uses for itables (average by class: %d bytes)", _total_size / K, _total_size / _total_classes);
1324 }
1325 
1326 #endif // PRODUCT
   1 /*
   2  * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   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
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *


 628       if (unchecked_method_at(index) == old_method) {
 629         put_method_at(new_method, index);
 630 
 631         if (RC_TRACE_IN_RANGE(0x00100000, 0x00400000)) {
 632           if (!(*trace_name_printed)) {
 633             // RC_TRACE_MESG macro has an embedded ResourceMark
 634             RC_TRACE_MESG(("adjust: name=%s",
 635                            Klass::cast(old_method->method_holder())->external_name()));
 636             *trace_name_printed = true;
 637           }
 638           // RC_TRACE macro has an embedded ResourceMark
 639           RC_TRACE(0x00100000, ("vtable method update: %s(%s)",
 640                                 new_method->name()->as_C_string(),
 641                                 new_method->signature()->as_C_string()));
 642         }
 643       }
 644     }
 645   }
 646 }
 647 
 648 // a vtable should never contain old or obsolete methods
 649 bool klassVtable::check_no_old_or_obsolete_entries() {
 650   for (int i = 0; i < length(); i++) {
 651     methodOop m = unchecked_method_at(i);
 652     if (m != NULL && (m->is_old() || m->is_obsolete())) {
 653       return false;
 654     }
 655   }
 656   return true;
 657 }
 658 
 659 void klassVtable::dump_vtable() {
 660   // adds a searchable prefix when RedefineClasses() tracing is enabled
 661   RC_TRACE_NO_CR(0x00004000, (""));
 662   tty->print_cr("vtable dump --");
 663   for (int i = 0; i < length(); i++) {
 664     methodOop m = unchecked_method_at(i);
 665     if (m != NULL) {
 666       RC_TRACE_NO_CR(0x00004000, (""));
 667       tty->print("      (%5d)  ", i);
 668       m->access_flags().print_on(tty);
 669       tty->print(" --  ");
 670       m->print_name(tty);
 671       tty->cr();
 672     }
 673   }
 674 }
 675 
 676 // CDS/RedefineClasses support - clear vtables so they can be reinitialized
 677 void klassVtable::clear_vtable() {
 678   for (int i = 0; i < _length; i++) table()[i].clear();
 679 }
 680 
 681 bool klassVtable::is_initialized() {
 682   return _length == 0 || table()[0].method() != NULL;
 683 }
 684 
 685 
 686 // Garbage collection
 687 void klassVtable::oop_follow_contents() {
 688   int len = length();
 689   for (int i = 0; i < len; i++) {
 690     MarkSweep::mark_and_push(adr_method_at(i));
 691   }
 692 }
 693 
 694 #ifndef SERIALGC
 695 void klassVtable::oop_follow_contents(ParCompactionManager* cm) {


1005     // The itable can describe more than one interface and the same
1006     // method signature can be specified by more than one interface.
1007     // This means we have to do an exhaustive search to find all the
1008     // old_method references.
1009     for (int i = 0; i < _size_method_table; i++) {
1010       if (ime->method() == old_method) {
1011         ime->initialize(new_method);
1012 
1013         if (RC_TRACE_IN_RANGE(0x00100000, 0x00400000)) {
1014           if (!(*trace_name_printed)) {
1015             // RC_TRACE_MESG macro has an embedded ResourceMark
1016             RC_TRACE_MESG(("adjust: name=%s",
1017               Klass::cast(old_method->method_holder())->external_name()));
1018             *trace_name_printed = true;
1019           }
1020           // RC_TRACE macro has an embedded ResourceMark
1021           RC_TRACE(0x00200000, ("itable method update: %s(%s)",
1022             new_method->name()->as_C_string(),
1023             new_method->signature()->as_C_string()));
1024         }
1025         // cannot 'break' here; see for-loop comment above.
1026       }
1027       ime++;
1028     }
1029   }
1030 }
1031 
1032 // an itable should never contain old or obsolete methods
1033 bool klassItable::check_no_old_or_obsolete_entries() {
1034   itableMethodEntry* ime = method_entry(0);
1035   for (int i = 0; i < _size_method_table; i++) {
1036     methodOop m = ime->method();
1037     if (m != NULL && (m->is_old() || m->is_obsolete())) {
1038       return false;
1039     }
1040     ime++;
1041   }
1042   return true;
1043 }
1044 
1045 void klassItable::dump_itable() {
1046   itableMethodEntry* ime = method_entry(0);
1047   // adds a searchable prefix when RedefineClasses() tracing is enabled
1048   RC_TRACE_NO_CR(0x00004000, (""));
1049   tty->print_cr("itable dump --");
1050   for (int i = 0; i < _size_method_table; i++) {
1051     methodOop m = ime->method();
1052     if (m != NULL) {
1053       RC_TRACE_NO_CR(0x00004000, (""));
1054       tty->print("      (%5d)  ", i);
1055       m->access_flags().print_on(tty);
1056       tty->print(" --  ");
1057       m->print_name(tty);
1058       tty->cr();
1059     }
1060     ime++;
1061   }
1062 }
1063 
1064 
1065 // Setup
1066 class InterfaceVisiterClosure : public StackObj {
1067  public:
1068   virtual void doit(klassOop intf, int method_count) = 0;
1069 };
1070 
1071 // Visit all interfaces with at-least one method (excluding <clinit>)
1072 void visit_all_interfaces(objArrayOop transitive_intf, InterfaceVisiterClosure *blk) {
1073   // Handle array argument
1074   for(int i = 0; i < transitive_intf->length(); i++) {
1075     klassOop intf = (klassOop)transitive_intf->obj_at(i);
1076     assert(Klass::cast(intf)->is_interface(), "sanity check");
1077 
1078     // Find no. of methods excluding a <clinit>
1079     int method_count = instanceKlass::cast(intf)->methods()->length();
1080     if (method_count > 0) {
1081       methodOop m = (methodOop)instanceKlass::cast(intf)->methods()->obj_at(0);
1082       assert(m != NULL && m->is_method(), "sanity check");
1083       if (m->name() == vmSymbols::object_initializer_name()) {
1084         method_count--;


1330 int VtableStats::sum_of_vtable_len = 0;
1331 int VtableStats::sum_of_array_vtable_len = 0;
1332 int VtableStats::fixed = 0;
1333 int VtableStats::filler = 0;
1334 int VtableStats::entries = 0;
1335 int VtableStats::array_entries = 0;
1336 
1337 void klassVtable::print_statistics() {
1338   ResourceMark rm;
1339   HandleMark hm;
1340   VtableStats::compute();
1341   tty->print_cr("vtable statistics:");
1342   tty->print_cr("%6d classes (%d instance, %d array)", VtableStats::no_klasses, VtableStats::no_instance_klasses, VtableStats::no_array_klasses);
1343   int total = VtableStats::fixed + VtableStats::filler + VtableStats::entries;
1344   tty->print_cr("%6d bytes fixed overhead (refs + vtable object header)", VtableStats::fixed);
1345   tty->print_cr("%6d bytes filler overhead", VtableStats::filler);
1346   tty->print_cr("%6d bytes for vtable entries (%d for arrays)", VtableStats::entries, VtableStats::array_entries);
1347   tty->print_cr("%6d bytes total", total);
1348 }
1349 



























1350 int  klassItable::_total_classes;   // Total no. of classes with itables
1351 long klassItable::_total_size;      // Total no. of bytes used for itables
1352 
1353 void klassItable::print_statistics() {
1354  tty->print_cr("itable statistics:");
1355  tty->print_cr("%6d classes with itables", _total_classes);
1356  tty->print_cr("%6d K uses for itables (average by class: %d bytes)", _total_size / K, _total_size / _total_classes);
1357 }
1358 
1359 #endif // PRODUCT