1678 return deflated_count;
1679 }
1680
1681 void ObjectSynchronizer::deflate_idle_monitors() {
1682 assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
1683 int nInuse = 0; // currently associated with objects
1684 int nInCirculation = 0; // extant
1685 int nScavenged = 0; // reclaimed
1686 bool deflated = false;
1687
1688 ObjectMonitor * freeHeadp = NULL; // Local SLL of scavenged monitors
1689 ObjectMonitor * freeTailp = NULL;
1690
1691 TEVENT(deflate_idle_monitors);
1692 // Prevent omFlush from changing mids in Thread dtor's during deflation
1693 // And in case the vm thread is acquiring a lock during a safepoint
1694 // See e.g. 6320749
1695 Thread::muxAcquire(&gListLock, "scavenge - return");
1696
1697 if (MonitorInUseLists) {
1698 int inUse = 0;
1699 for (JavaThread* cur = Threads::first(); cur != NULL; cur = cur->next()) {
1700 nInCirculation+= cur->omInUseCount;
1701 int deflated_count = deflate_monitor_list(cur->omInUseList_addr(), &freeHeadp, &freeTailp);
1702 cur->omInUseCount-= deflated_count;
1703 if (ObjectMonitor::Knob_VerifyInUse) {
1704 verifyInUse(cur);
1705 }
1706 nScavenged += deflated_count;
1707 nInuse += cur->omInUseCount;
1708 }
1709
1710 // For moribund threads, scan gOmInUseList
1711 if (gOmInUseList) {
1712 nInCirculation += gOmInUseCount;
1713 int deflated_count = deflate_monitor_list((ObjectMonitor **)&gOmInUseList, &freeHeadp, &freeTailp);
1714 gOmInUseCount-= deflated_count;
1715 nScavenged += deflated_count;
1716 nInuse += gOmInUseCount;
1717 }
1718
1719 } else {
1720 PaddedEnd<ObjectMonitor> * block =
1721 (PaddedEnd<ObjectMonitor> *)OrderAccess::load_ptr_acquire(&gBlockList);
1722 for (; block != NULL; block = (PaddedEnd<ObjectMonitor> *)next(block)) {
1723 // Iterate over all extant monitors - Scavenge all idle monitors.
1724 assert(block->object() == CHAINMARKER, "must be a block header");
1725 nInCirculation += _BLOCKSIZE;
1726 for (int i = 1; i < _BLOCKSIZE; i++) {
1727 ObjectMonitor* mid = (ObjectMonitor*)&block[i];
1728 oop obj = (oop)mid->object();
1761
1762 ForceMonitorScavenge = 0; // Reset
1763
1764 // Move the scavenged monitors back to the global free list.
1765 if (freeHeadp != NULL) {
1766 guarantee(freeTailp != NULL && nScavenged > 0, "invariant");
1767 assert(freeTailp->FreeNext == NULL, "invariant");
1768 // constant-time list splice - prepend scavenged segment to gFreeList
1769 freeTailp->FreeNext = gFreeList;
1770 gFreeList = freeHeadp;
1771 }
1772 Thread::muxRelease(&gListLock);
1773
1774 OM_PERFDATA_OP(Deflations, inc(nScavenged));
1775 OM_PERFDATA_OP(MonExtant, set_value(nInCirculation));
1776
1777 // TODO: Add objectMonitor leak detection.
1778 // Audit/inventory the objectMonitors -- make sure they're all accounted for.
1779 GVars.stwRandom = os::random();
1780 GVars.stwCycle++;
1781 }
1782
1783 // Monitor cleanup on JavaThread::exit
1784
1785 // Iterate through monitor cache and attempt to release thread's monitors
1786 // Gives up on a particular monitor if an exception occurs, but continues
1787 // the overall iteration, swallowing the exception.
1788 class ReleaseJavaMonitorsClosure: public MonitorClosure {
1789 private:
1790 TRAPS;
1791
1792 public:
1793 ReleaseJavaMonitorsClosure(Thread* thread) : THREAD(thread) {}
1794 void do_monitor(ObjectMonitor* mid) {
1795 if (mid->owner() == THREAD) {
1796 if (ObjectMonitor::Knob_VerifyMatch != 0) {
1797 ResourceMark rm;
1798 Handle obj(THREAD, (oop) mid->object());
1799 tty->print("INFO: unexpected locked object:");
1800 javaVFrame::print_locked_object_class_name(tty, obj, "locked");
|
1678 return deflated_count;
1679 }
1680
1681 void ObjectSynchronizer::deflate_idle_monitors() {
1682 assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
1683 int nInuse = 0; // currently associated with objects
1684 int nInCirculation = 0; // extant
1685 int nScavenged = 0; // reclaimed
1686 bool deflated = false;
1687
1688 ObjectMonitor * freeHeadp = NULL; // Local SLL of scavenged monitors
1689 ObjectMonitor * freeTailp = NULL;
1690
1691 TEVENT(deflate_idle_monitors);
1692 // Prevent omFlush from changing mids in Thread dtor's during deflation
1693 // And in case the vm thread is acquiring a lock during a safepoint
1694 // See e.g. 6320749
1695 Thread::muxAcquire(&gListLock, "scavenge - return");
1696
1697 if (MonitorInUseLists) {
1698 // Note: the thread-local monitors lists get deflated in
1699 // a separate pass. See deflate_thread_local_monitors().
1700
1701 // For moribund threads, scan gOmInUseList
1702 if (gOmInUseList) {
1703 nInCirculation += gOmInUseCount;
1704 int deflated_count = deflate_monitor_list((ObjectMonitor **)&gOmInUseList, &freeHeadp, &freeTailp);
1705 gOmInUseCount-= deflated_count;
1706 nScavenged += deflated_count;
1707 nInuse += gOmInUseCount;
1708 }
1709
1710 } else {
1711 PaddedEnd<ObjectMonitor> * block =
1712 (PaddedEnd<ObjectMonitor> *)OrderAccess::load_ptr_acquire(&gBlockList);
1713 for (; block != NULL; block = (PaddedEnd<ObjectMonitor> *)next(block)) {
1714 // Iterate over all extant monitors - Scavenge all idle monitors.
1715 assert(block->object() == CHAINMARKER, "must be a block header");
1716 nInCirculation += _BLOCKSIZE;
1717 for (int i = 1; i < _BLOCKSIZE; i++) {
1718 ObjectMonitor* mid = (ObjectMonitor*)&block[i];
1719 oop obj = (oop)mid->object();
1752
1753 ForceMonitorScavenge = 0; // Reset
1754
1755 // Move the scavenged monitors back to the global free list.
1756 if (freeHeadp != NULL) {
1757 guarantee(freeTailp != NULL && nScavenged > 0, "invariant");
1758 assert(freeTailp->FreeNext == NULL, "invariant");
1759 // constant-time list splice - prepend scavenged segment to gFreeList
1760 freeTailp->FreeNext = gFreeList;
1761 gFreeList = freeHeadp;
1762 }
1763 Thread::muxRelease(&gListLock);
1764
1765 OM_PERFDATA_OP(Deflations, inc(nScavenged));
1766 OM_PERFDATA_OP(MonExtant, set_value(nInCirculation));
1767
1768 // TODO: Add objectMonitor leak detection.
1769 // Audit/inventory the objectMonitors -- make sure they're all accounted for.
1770 GVars.stwRandom = os::random();
1771 GVars.stwCycle++;
1772 }
1773
1774 void ObjectSynchronizer::deflate_thread_local_monitors(Thread* thread) {
1775 assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
1776 if (! MonitorInUseLists) return;
1777
1778 ObjectMonitor * freeHeadp = NULL; // Local SLL of scavenged monitors
1779 ObjectMonitor * freeTailp = NULL;
1780
1781 int deflated_count = deflate_monitor_list(thread->omInUseList_addr(), &freeHeadp, &freeTailp);
1782 thread->omInUseCount-= deflated_count;
1783 if (ObjectMonitor::Knob_VerifyInUse) {
1784 verifyInUse(thread);
1785 }
1786
1787 // Move the scavenged monitors back to the global free list.
1788 if (freeHeadp != NULL) {
1789 Thread::muxAcquire(&gListLock, "scavenge - return");
1790 guarantee(freeTailp != NULL && deflated_count > 0, "invariant");
1791 assert(freeTailp->FreeNext == NULL, "invariant");
1792
1793 gMonitorFreeCount += deflated_count;
1794 // constant-time list splice - prepend scavenged segment to gFreeList
1795 freeTailp->FreeNext = gFreeList;
1796 gFreeList = freeHeadp;
1797 Thread::muxRelease(&gListLock);
1798 }
1799 }
1800
1801 // Monitor cleanup on JavaThread::exit
1802
1803 // Iterate through monitor cache and attempt to release thread's monitors
1804 // Gives up on a particular monitor if an exception occurs, but continues
1805 // the overall iteration, swallowing the exception.
1806 class ReleaseJavaMonitorsClosure: public MonitorClosure {
1807 private:
1808 TRAPS;
1809
1810 public:
1811 ReleaseJavaMonitorsClosure(Thread* thread) : THREAD(thread) {}
1812 void do_monitor(ObjectMonitor* mid) {
1813 if (mid->owner() == THREAD) {
1814 if (ObjectMonitor::Knob_VerifyMatch != 0) {
1815 ResourceMark rm;
1816 Handle obj(THREAD, (oop) mid->object());
1817 tty->print("INFO: unexpected locked object:");
1818 javaVFrame::print_locked_object_class_name(tty, obj, "locked");
|