hotspot/src/share/vm/oops/methodData.cpp
changeset 23845 ebd1fafcc362
parent 23526 6851d341ad52
child 24351 61b33cc6d3cf
equal deleted inserted replaced
23844:0c29a324ae14 23845:ebd1fafcc362
  1529       *ptr = 0;
  1529       *ptr = 0;
  1530     }
  1530     }
  1531   }
  1531   }
  1532 }
  1532 }
  1533 
  1533 
  1534 // Remove SpeculativeTrapData entries that reference an unloaded
  1534 class CleanExtraDataClosure : public StackObj {
  1535 // method
  1535 public:
  1536 void MethodData::clean_extra_data(BoolObjectClosure* is_alive) {
  1536   virtual bool is_live(Method* m) = 0;
       
  1537 };
       
  1538 
       
  1539 // Check for entries that reference an unloaded method
       
  1540 class CleanExtraDataKlassClosure : public CleanExtraDataClosure {
       
  1541 private:
       
  1542   BoolObjectClosure* _is_alive;
       
  1543 public:
       
  1544   CleanExtraDataKlassClosure(BoolObjectClosure* is_alive) : _is_alive(is_alive) {}
       
  1545   bool is_live(Method* m) {
       
  1546     return m->method_holder()->is_loader_alive(_is_alive);
       
  1547   }
       
  1548 };
       
  1549 
       
  1550 // Check for entries that reference a redefined method
       
  1551 class CleanExtraDataMethodClosure : public CleanExtraDataClosure {
       
  1552 public:
       
  1553   CleanExtraDataMethodClosure() {}
       
  1554   bool is_live(Method* m) {
       
  1555     return m->on_stack();
       
  1556   }
       
  1557 };
       
  1558 
       
  1559 
       
  1560 // Remove SpeculativeTrapData entries that reference an unloaded or
       
  1561 // redefined method
       
  1562 void MethodData::clean_extra_data(CleanExtraDataClosure* cl) {
  1537   DataLayout* dp  = extra_data_base();
  1563   DataLayout* dp  = extra_data_base();
  1538   DataLayout* end = extra_data_limit();
  1564   DataLayout* end = extra_data_limit();
  1539 
  1565 
  1540   int shift = 0;
  1566   int shift = 0;
  1541   for (; dp < end; dp = next_extra(dp)) {
  1567   for (; dp < end; dp = next_extra(dp)) {
  1542     switch(dp->tag()) {
  1568     switch(dp->tag()) {
  1543     case DataLayout::speculative_trap_data_tag: {
  1569     case DataLayout::speculative_trap_data_tag: {
  1544       SpeculativeTrapData* data = new SpeculativeTrapData(dp);
  1570       SpeculativeTrapData* data = new SpeculativeTrapData(dp);
  1545       Method* m = data->method();
  1571       Method* m = data->method();
  1546       assert(m != NULL, "should have a method");
  1572       assert(m != NULL, "should have a method");
  1547       if (!m->method_holder()->is_loader_alive(is_alive)) {
  1573       if (!cl->is_live(m)) {
  1548         // "shift" accumulates the number of cells for dead
  1574         // "shift" accumulates the number of cells for dead
  1549         // SpeculativeTrapData entries that have been seen so
  1575         // SpeculativeTrapData entries that have been seen so
  1550         // far. Following entries must be shifted left by that many
  1576         // far. Following entries must be shifted left by that many
  1551         // cells to remove the dead SpeculativeTrapData entries.
  1577         // cells to remove the dead SpeculativeTrapData entries.
  1552         shift += (int)((intptr_t*)next_extra(dp) - (intptr_t*)dp);
  1578         shift += (int)((intptr_t*)next_extra(dp) - (intptr_t*)dp);
  1573       fatal(err_msg("unexpected tag %d", dp->tag()));
  1599       fatal(err_msg("unexpected tag %d", dp->tag()));
  1574     }
  1600     }
  1575   }
  1601   }
  1576 }
  1602 }
  1577 
  1603 
  1578 // Verify there's no unloaded method referenced by a
  1604 // Verify there's no unloaded or redefined method referenced by a
  1579 // SpeculativeTrapData entry
  1605 // SpeculativeTrapData entry
  1580 void MethodData::verify_extra_data_clean(BoolObjectClosure* is_alive) {
  1606 void MethodData::verify_extra_data_clean(CleanExtraDataClosure* cl) {
  1581 #ifdef ASSERT
  1607 #ifdef ASSERT
  1582   DataLayout* dp  = extra_data_base();
  1608   DataLayout* dp  = extra_data_base();
  1583   DataLayout* end = extra_data_limit();
  1609   DataLayout* end = extra_data_limit();
  1584 
  1610 
  1585   for (; dp < end; dp = next_extra(dp)) {
  1611   for (; dp < end; dp = next_extra(dp)) {
  1586     switch(dp->tag()) {
  1612     switch(dp->tag()) {
  1587     case DataLayout::speculative_trap_data_tag: {
  1613     case DataLayout::speculative_trap_data_tag: {
  1588       SpeculativeTrapData* data = new SpeculativeTrapData(dp);
  1614       SpeculativeTrapData* data = new SpeculativeTrapData(dp);
  1589       Method* m = data->method();
  1615       Method* m = data->method();
  1590       assert(m != NULL && m->method_holder()->is_loader_alive(is_alive), "Method should exist");
  1616       assert(m != NULL && cl->is_live(m), "Method should exist");
  1591       break;
  1617       break;
  1592     }
  1618     }
  1593     case DataLayout::bit_data_tag:
  1619     case DataLayout::bit_data_tag:
  1594       continue;
  1620       continue;
  1595     case DataLayout::no_tag:
  1621     case DataLayout::no_tag:
  1611   ParametersTypeData* parameters = parameters_type_data();
  1637   ParametersTypeData* parameters = parameters_type_data();
  1612   if (parameters != NULL) {
  1638   if (parameters != NULL) {
  1613     parameters->clean_weak_klass_links(is_alive);
  1639     parameters->clean_weak_klass_links(is_alive);
  1614   }
  1640   }
  1615 
  1641 
  1616   clean_extra_data(is_alive);
  1642   CleanExtraDataKlassClosure cl(is_alive);
  1617   verify_extra_data_clean(is_alive);
  1643   clean_extra_data(&cl);
  1618 }
  1644   verify_extra_data_clean(&cl);
       
  1645 }
       
  1646 
       
  1647 void MethodData::clean_weak_method_links() {
       
  1648   for (ProfileData* data = first_data();
       
  1649        is_valid(data);
       
  1650        data = next_data(data)) {
       
  1651     data->clean_weak_method_links();
       
  1652   }
       
  1653 
       
  1654   CleanExtraDataMethodClosure cl;
       
  1655   clean_extra_data(&cl);
       
  1656   verify_extra_data_clean(&cl);
       
  1657 }