|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
|
|
package sun.management; |
|
|
|
import java.lang.management.ManagementFactory; |
|
import java.lang.management.MemoryPoolMXBean; |
|
import java.lang.management.MemoryUsage; |
|
import java.lang.management.MemoryType; |
|
import java.lang.management.MemoryManagerMXBean; |
|
import javax.management.openmbean.CompositeData; |
|
import javax.management.ObjectName; |
|
|
|
import static java.lang.management.MemoryNotificationInfo.*; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
class MemoryPoolImpl implements MemoryPoolMXBean { |
|
|
|
private final String name; |
|
private final boolean isHeap; |
|
private final boolean isValid; |
|
private final boolean collectionThresholdSupported; |
|
private final boolean usageThresholdSupported; |
|
|
|
private MemoryManagerMXBean[] managers; |
|
|
|
private long usageThreshold; |
|
private long collectionThreshold; |
|
|
|
private boolean usageSensorRegistered; |
|
private boolean gcSensorRegistered; |
|
private Sensor usageSensor; |
|
private Sensor gcSensor; |
|
|
|
MemoryPoolImpl(String name, boolean isHeap, long usageThreshold, |
|
long gcThreshold) { |
|
this.name = name; |
|
this.isHeap = isHeap; |
|
this.isValid = true; |
|
this.managers = null; |
|
this.usageThreshold = usageThreshold; |
|
this.collectionThreshold = gcThreshold; |
|
this.usageThresholdSupported = (usageThreshold >= 0); |
|
this.collectionThresholdSupported = (gcThreshold >= 0); |
|
this.usageSensor = new PoolSensor(this, name + " usage sensor"); |
|
this.gcSensor = new CollectionSensor(this, name + " collection sensor"); |
|
this.usageSensorRegistered = false; |
|
this.gcSensorRegistered = false; |
|
} |
|
|
|
public String getName() { |
|
return name; |
|
} |
|
|
|
public boolean isValid() { |
|
return isValid; |
|
} |
|
|
|
public MemoryType getType() { |
|
if (isHeap) { |
|
return MemoryType.HEAP; |
|
} else { |
|
return MemoryType.NON_HEAP; |
|
} |
|
} |
|
|
|
public MemoryUsage getUsage() { |
|
return getUsage0(); |
|
} |
|
|
|
public synchronized MemoryUsage getPeakUsage() { |
|
|
|
return getPeakUsage0(); |
|
} |
|
|
|
public synchronized long getUsageThreshold() { |
|
if (!isUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"Usage threshold is not supported"); |
|
} |
|
return usageThreshold; |
|
} |
|
|
|
public void setUsageThreshold(long newThreshold) { |
|
if (!isUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"Usage threshold is not supported"); |
|
} |
|
|
|
Util.checkControlAccess(); |
|
|
|
MemoryUsage usage = getUsage0(); |
|
if (newThreshold < 0) { |
|
throw new IllegalArgumentException( |
|
"Invalid threshold: " + newThreshold); |
|
} |
|
|
|
if (usage.getMax() != -1 && newThreshold > usage.getMax()) { |
|
throw new IllegalArgumentException( |
|
"Invalid threshold: " + newThreshold + |
|
" must be <= maxSize." + |
|
" Committed = " + usage.getCommitted() + |
|
" Max = " + usage.getMax()); |
|
} |
|
|
|
synchronized (this) { |
|
if (!usageSensorRegistered) { |
|
|
|
usageSensorRegistered = true; |
|
setPoolUsageSensor(usageSensor); |
|
} |
|
setUsageThreshold0(usageThreshold, newThreshold); |
|
this.usageThreshold = newThreshold; |
|
} |
|
} |
|
|
|
private synchronized MemoryManagerMXBean[] getMemoryManagers() { |
|
if (managers == null) { |
|
managers = getMemoryManagers0(); |
|
} |
|
return managers; |
|
} |
|
|
|
public String[] getMemoryManagerNames() { |
|
MemoryManagerMXBean[] mgrs = getMemoryManagers(); |
|
|
|
String[] names = new String[mgrs.length]; |
|
for (int i = 0; i < mgrs.length; i++) { |
|
names[i] = mgrs[i].getName(); |
|
} |
|
return names; |
|
} |
|
|
|
public void resetPeakUsage() { |
|
Util.checkControlAccess(); |
|
|
|
synchronized (this) { |
|
|
|
resetPeakUsage0(); |
|
} |
|
} |
|
|
|
public boolean isUsageThresholdExceeded() { |
|
if (!isUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"Usage threshold is not supported"); |
|
} |
|
|
|
|
|
if (usageThreshold == 0) { |
|
return false; |
|
} |
|
|
|
MemoryUsage u = getUsage0(); |
|
return (u.getUsed() >= usageThreshold || |
|
usageSensor.isOn()); |
|
} |
|
|
|
public long getUsageThresholdCount() { |
|
if (!isUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"Usage threshold is not supported"); |
|
} |
|
|
|
return usageSensor.getCount(); |
|
} |
|
|
|
public boolean isUsageThresholdSupported() { |
|
return usageThresholdSupported; |
|
} |
|
|
|
public synchronized long getCollectionUsageThreshold() { |
|
if (!isCollectionUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"CollectionUsage threshold is not supported"); |
|
} |
|
|
|
return collectionThreshold; |
|
} |
|
|
|
public void setCollectionUsageThreshold(long newThreshold) { |
|
if (!isCollectionUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"CollectionUsage threshold is not supported"); |
|
} |
|
|
|
Util.checkControlAccess(); |
|
|
|
MemoryUsage usage = getUsage0(); |
|
if (newThreshold < 0) { |
|
throw new IllegalArgumentException( |
|
"Invalid threshold: " + newThreshold); |
|
} |
|
|
|
if (usage.getMax() != -1 && newThreshold > usage.getMax()) { |
|
throw new IllegalArgumentException( |
|
"Invalid threshold: " + newThreshold + |
|
" > max (" + usage.getMax() + ")."); |
|
} |
|
|
|
synchronized (this) { |
|
if (!gcSensorRegistered) { |
|
|
|
gcSensorRegistered = true; |
|
setPoolCollectionSensor(gcSensor); |
|
} |
|
setCollectionThreshold0(collectionThreshold, newThreshold); |
|
this.collectionThreshold = newThreshold; |
|
} |
|
} |
|
|
|
public boolean isCollectionUsageThresholdExceeded() { |
|
if (!isCollectionUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"CollectionUsage threshold is not supported"); |
|
} |
|
|
|
|
|
if (collectionThreshold == 0) { |
|
return false; |
|
} |
|
|
|
MemoryUsage u = getCollectionUsage0(); |
|
return (gcSensor.isOn() || |
|
(u != null && u.getUsed() >= collectionThreshold)); |
|
} |
|
|
|
public long getCollectionUsageThresholdCount() { |
|
if (!isCollectionUsageThresholdSupported()) { |
|
throw new UnsupportedOperationException( |
|
"CollectionUsage threshold is not supported"); |
|
} |
|
|
|
return gcSensor.getCount(); |
|
} |
|
|
|
public MemoryUsage getCollectionUsage() { |
|
return getCollectionUsage0(); |
|
} |
|
|
|
public boolean isCollectionUsageThresholdSupported() { |
|
return collectionThresholdSupported; |
|
} |
|
|
|
|
|
private native MemoryUsage getUsage0(); |
|
private native MemoryUsage getPeakUsage0(); |
|
private native MemoryUsage getCollectionUsage0(); |
|
private native void setUsageThreshold0(long current, long newThreshold); |
|
private native void setCollectionThreshold0(long current, long newThreshold); |
|
private native void resetPeakUsage0(); |
|
private native MemoryManagerMXBean[] getMemoryManagers0(); |
|
private native void setPoolUsageSensor(Sensor s); |
|
private native void setPoolCollectionSensor(Sensor s); |
|
|
|
// package private |
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
class PoolSensor extends Sensor { |
|
MemoryPoolImpl pool; |
|
|
|
PoolSensor(MemoryPoolImpl pool, String name) { |
|
super(name); |
|
this.pool = pool; |
|
} |
|
void triggerAction(MemoryUsage usage) { |
|
|
|
MemoryImpl.createNotification(MEMORY_THRESHOLD_EXCEEDED, |
|
pool.getName(), |
|
usage, |
|
getCount()); |
|
} |
|
void triggerAction() { |
|
// do nothing |
|
} |
|
void clearAction() { |
|
// do nothing |
|
} |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
class CollectionSensor extends Sensor { |
|
MemoryPoolImpl pool; |
|
CollectionSensor(MemoryPoolImpl pool, String name) { |
|
super(name); |
|
this.pool = pool; |
|
} |
|
void triggerAction(MemoryUsage usage) { |
|
MemoryImpl.createNotification(MEMORY_COLLECTION_THRESHOLD_EXCEEDED, |
|
pool.getName(), |
|
usage, |
|
gcSensor.getCount()); |
|
} |
|
void triggerAction() { |
|
// do nothing |
|
} |
|
void clearAction() { |
|
// do nothing |
|
} |
|
} |
|
|
|
public ObjectName getObjectName() { |
|
return Util.newObjectName(ManagementFactory.MEMORY_POOL_MXBEAN_DOMAIN_TYPE, getName()); |
|
} |
|
|
|
} |