提交 01ef1bee 编写于 作者: A alanb

Merge

......@@ -12,3 +12,4 @@ fa4c0a6cdd25d97d4e6f5d7aa180bcbb0e0d56af jdk7-b33
cf4894b78ceb966326e93bf221db0c2d14d59218 jdk7-b35
134fd1a656ea85acd1f97f6700f75029b9b472a0 jdk7-b36
14f50aee4989b75934d385c56a83da0c23d2f68b jdk7-b37
cc5f810b5af8a3a83b0df5a29d9e24d7a0ff8086 jdk7-b38
......@@ -44,13 +44,13 @@
<!-- because they depend on the values of BUILD_DATE and BUILD_DATE_SIMPLE -->
<!-- At this time, ./build.properties has not been loaded yet. -->
<property name="project.build.name" value="openjdk-bXX"/>
<property name="project.build.fulltag"
<property name="project.build.fulltag"
value="${ant.project.name}-${project.build.name}-${BUILD_DATE}" />
<!-- unchecked warnings will be fixed in JMX 2.0 as part of the work
being done on JSR 255 new features -->
<property name="javac.options"
value="-Xlint -Xlint:-unchecked -Xlint:-deprecation"/>
<property name="javac.options"
value="-Xlint -Xlint:-deprecation"/>
</target>
......@@ -58,13 +58,13 @@
<!-- Dir to keep generated stub source -->
<mkdir dir="${gensrc.dir}" />
</target>
<!-- ~~~~~~~~~~~~~~~~~~~~~~~~~ -->
<!-- Call rmic-jmx subtargets -->
<target name="-rmic-jmx" depends="-init,-rmic-jmx-jrmp,-rmic-jmx-iiop"
description="Calls -init,-rmic-jmx-jrmp,-rmic-jmx-iiop"
description="Calls -init,-rmic-jmx-jrmp,-rmic-jmx-iiop"
/>
......@@ -96,7 +96,7 @@
<target name="-rmic-jmx-iiop" depends="-init,-check-jmx-iiop-uptodate" unless="jmx-iiop-uptodate"
description="Generate RMI IIOP stub class files for remote objects. Do not keep generated java files." >
<rmic base="${classes.dir}"
includeAntRuntime="no"
includeJavaRuntime="no"
......@@ -115,11 +115,11 @@
<target name="-check-jmx-iiop-uptodate" depends="-init">
<uptodate property="jmx-iiop-uptodate"
<uptodate property="jmx-iiop-uptodate"
srcfile="${classes.dir}/javax/management/remote/rmi/RMIConnectionImpl.class"
targetfile="${classes.dir}/org/omg/stub/javax/management/remote/rmi/_RMIConnectionImpl_Tie.class"
/>
<uptodate property="jmx-iiop-uptodate"
<uptodate property="jmx-iiop-uptodate"
srcfile="${classes.dir}/javax/management/remote/rmi/RMIServerImpl.class"
targetfile="${classes.dir}/org/omg/stub/javax/management/remote/rmi/_RMIServerImpl_Tie.class"
/>
......@@ -131,7 +131,7 @@
<target name="-post-compile" depends="-init,-rmic-jmx"
description="Jar JMX class files (including RMI stubs)" >
<mkdir dir="${dist.dir}/lib"/>
<jar jarfile="${dist.dir}/lib/${jar.jmx.name}"
<jar jarfile="${dist.dir}/lib/${jar.jmx.name}"
update="true"
index="false"
duplicate="fail">
......@@ -144,7 +144,7 @@
<attribute name="Specification-Version" value="${jar.jmx.spec.version}" />
<attribute name="Specification-Vendor" value="${jar.jmx.spec.vendor}" />
<attribute name="Implementation-Title" value="${jar.jmx.impl.title}" />
<attribute name="Implementation-Version" value="${project.build.fulltag}" />
<attribute name="Implementation-Version" value="${project.build.fulltag}" />
<attribute name="Implementation-Vendor" value="${jar.jmx.impl.vendor}" />
</section>
</manifest>
......
......@@ -69,9 +69,9 @@ public class ServiceName {
/**
* The version of the JMX specification implemented by this product.
* <BR>
* The value is <CODE>1.4</CODE>.
* The value is <CODE>2.0</CODE>.
*/
public static final String JMX_SPEC_VERSION = "1.4";
public static final String JMX_SPEC_VERSION = "2.0";
/**
* The vendor of the JMX specification implemented by this product.
......
......@@ -41,7 +41,7 @@ public class EventParams {
@SuppressWarnings("cast") // cast for jdk 1.5
public static long getLeaseTimeout() {
long timeout = EventClient.DEFAULT_LEASE_TIMEOUT;
long timeout = EventClient.DEFAULT_REQUESTED_LEASE_TIME;
try {
final GetPropertyAction act =
new GetPropertyAction(DEFAULT_LEASE_TIMEOUT);
......
......@@ -29,6 +29,7 @@ import com.sun.jmx.remote.util.ClassLogger;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.TimeUnit;
/**
......@@ -141,11 +142,12 @@ public class LeaseManager {
}
private final Runnable callback;
private ScheduledFuture scheduled; // If null, the lease has expired.
private ScheduledFuture<?> scheduled; // If null, the lease has expired.
private static final ThreadFactory threadFactory =
new DaemonThreadFactory("JMX LeaseManager %d");
private final ScheduledExecutorService executor
= Executors.newScheduledThreadPool(1,
new DaemonThreadFactory("JMX LeaseManager %d"));
= Executors.newScheduledThreadPool(1, threadFactory);
private static final ClassLogger logger =
new ClassLogger("javax.management.event", "LeaseManager");
......
......@@ -128,7 +128,7 @@ public class LeaseRenewer {
};
private final Callable<Long> doRenew;
private ScheduledFuture future;
private ScheduledFuture<?> future;
private boolean closed = false;
private long nextRenewTime;
......
......@@ -247,7 +247,7 @@ public class DefaultMBeanServerInterceptor
MBeanRegistrationException, MBeanException,
NotCompliantMBeanException, InstanceNotFoundException {
Class theClass;
Class<?> theClass;
if (className == null) {
final RuntimeException wrapped =
......@@ -327,7 +327,7 @@ public class DefaultMBeanServerInterceptor
// ------------------------------
// ------------------------------
Class theClass = object.getClass();
Class<?> theClass = object.getClass();
Introspector.checkCompliance(theClass);
......@@ -808,9 +808,8 @@ public class DefaultMBeanServerInterceptor
// on each specific attribute
//
allowedAttributes = new AttributeList(attributes.size());
for (Iterator i = attributes.iterator(); i.hasNext();) {
for (Attribute attribute : attributes.asList()) {
try {
Attribute attribute = (Attribute) i.next();
checkMBeanPermission(mbeanServerName, classname, attribute.getName(),
name, "setAttribute");
allowedAttributes.add(attribute);
......@@ -1857,7 +1856,7 @@ public class DefaultMBeanServerInterceptor
}
}
private static void checkMBeanTrustPermission(final Class theClass)
private static void checkMBeanTrustPermission(final Class<?> theClass)
throws SecurityException {
SecurityManager sm = System.getSecurityManager();
if (sm != null) {
......
......@@ -55,9 +55,19 @@ import javax.management.namespace.JMXNamespaces;
import javax.management.namespace.MBeanServerSupport;
import javax.management.remote.IdentityMBeanServerForwarder;
/**
* <p>An {@link MBeanServerForwarder} that simulates the existence of a
* given MBean. Requests for that MBean, call it X, are intercepted by the
* forwarder, and requests for any other MBean are forwarded to the next
* forwarder in the chain. Requests such as queryNames which can span both the
* X and other MBeans are handled by merging the results for X with the results
* from the next forwarder, unless the "visible" parameter is false, in which
* case X is invisible to such requests.</p>
*/
public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
private final ObjectName mbeanName;
private final boolean visible;
private DynamicMBean mbean;
private MBeanServer mbeanMBS = new MBeanServerSupport() {
......@@ -85,10 +95,20 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
return null;
}
// This will only be called if mbeanName has an empty domain.
// In that case a getAttribute (e.g.) of that name will have the
// domain replaced by MBeanServerSupport with the default domain,
// so we must be sure that the default domain is empty too.
@Override
public String getDefaultDomain() {
return mbeanName.getDomain();
}
};
public SingleMBeanForwarder(ObjectName mbeanName, DynamicMBean mbean) {
public SingleMBeanForwarder(
ObjectName mbeanName, DynamicMBean mbean, boolean visible) {
this.mbeanName = mbeanName;
this.visible = visible;
setSingleMBean(mbean);
}
......@@ -213,8 +233,10 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
@Override
public String[] getDomains() {
TreeSet<String> domainSet =
new TreeSet<String>(Arrays.asList(super.getDomains()));
String[] domains = super.getDomains();
if (!visible)
return domains;
TreeSet<String> domainSet = new TreeSet<String>(Arrays.asList(domains));
domainSet.add(mbeanName.getDomain());
return domainSet.toArray(new String[domainSet.size()]);
}
......@@ -222,7 +244,7 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
@Override
public Integer getMBeanCount() {
Integer count = super.getMBeanCount();
if (!super.isRegistered(mbeanName))
if (visible && !super.isRegistered(mbeanName))
count++;
return count;
}
......@@ -284,7 +306,7 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
*/
private boolean applies(ObjectName pattern) {
// we know pattern is not null.
if (!pattern.apply(mbeanName))
if (!visible || !pattern.apply(mbeanName))
return false;
final String dompat = pattern.getDomain();
......@@ -306,10 +328,12 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
@Override
public Set<ObjectInstance> queryMBeans(ObjectName name, QueryExp query) {
Set<ObjectInstance> names = super.queryMBeans(name, query);
if (name == null || applies(name) ) {
// Don't assume mbs.queryNames returns a writable set.
names = Util.cloneSet(names);
names.addAll(mbeanMBS.queryMBeans(name, query));
if (visible) {
if (name == null || applies(name) ) {
// Don't assume mbs.queryNames returns a writable set.
names = Util.cloneSet(names);
names.addAll(mbeanMBS.queryMBeans(name, query));
}
}
return names;
}
......@@ -317,10 +341,12 @@ public class SingleMBeanForwarder extends IdentityMBeanServerForwarder {
@Override
public Set<ObjectName> queryNames(ObjectName name, QueryExp query) {
Set<ObjectName> names = super.queryNames(name, query);
if (name == null || applies(name)) {
// Don't assume mbs.queryNames returns a writable set.
names = Util.cloneSet(names);
names.addAll(mbeanMBS.queryNames(name, query));
if (visible) {
if (name == null || applies(name)) {
// Don't assume mbs.queryNames returns a writable set.
names = Util.cloneSet(names);
names.addAll(mbeanMBS.queryNames(name, query));
}
}
return names;
}
......
......@@ -136,14 +136,14 @@ final class ClassLoaderRepositorySupport
new Hashtable<ObjectName,ClassLoader>(10);
// from javax.management.loading.DefaultLoaderRepository
public final Class loadClass(String className)
public final Class<?> loadClass(String className)
throws ClassNotFoundException {
return loadClass(loaders, className, null, null);
}
// from javax.management.loading.DefaultLoaderRepository
public final Class loadClassWithout(ClassLoader without, String className)
public final Class<?> loadClassWithout(ClassLoader without, String className)
throws ClassNotFoundException {
if (MBEANSERVER_LOGGER.isLoggable(Level.FINER)) {
MBEANSERVER_LOGGER.logp(Level.FINER,
......@@ -167,7 +167,7 @@ final class ClassLoaderRepositorySupport
}
public final Class loadClassBefore(ClassLoader stop, String className)
public final Class<?> loadClassBefore(ClassLoader stop, String className)
throws ClassNotFoundException {
if (MBEANSERVER_LOGGER.isLoggable(Level.FINER)) {
MBEANSERVER_LOGGER.logp(Level.FINER,
......@@ -187,10 +187,10 @@ final class ClassLoaderRepositorySupport
}
private Class loadClass(final LoaderEntry list[],
final String className,
final ClassLoader without,
final ClassLoader stop)
private Class<?> loadClass(final LoaderEntry list[],
final String className,
final ClassLoader without,
final ClassLoader stop)
throws ClassNotFoundException {
final int size = list.length;
for(int i=0; i<size; i++) {
......
......@@ -68,12 +68,12 @@ final class ConvertingMethod {
return method.getName();
}
OpenType getOpenReturnType() {
OpenType<?> getOpenReturnType() {
return returnMapping.getOpenType();
}
OpenType[] getOpenParameterTypes() {
final OpenType[] types = new OpenType[paramMappings.length];
OpenType<?>[] getOpenParameterTypes() {
final OpenType<?>[] types = new OpenType<?>[paramMappings.length];
for (int i = 0; i < paramMappings.length; i++)
types[i] = paramMappings[i].getOpenType();
return types;
......
......@@ -115,7 +115,7 @@ public class Introspector {
* Dynamic MBeans, <code>false</code> otherwise.
*
**/
public static final boolean isDynamic(final Class c) {
public static final boolean isDynamic(final Class<?> c) {
// Check if the MBean implements the DynamicMBean interface
return javax.management.DynamicMBean.class.isAssignableFrom(c);
}
......@@ -134,7 +134,7 @@ public class Introspector {
* MBeanServer.
*
**/
public static void testCreation(Class c)
public static void testCreation(Class<?> c)
throws NotCompliantMBeanException {
// Check if the class is a concrete class
final int mods = c.getModifiers();
......@@ -143,7 +143,7 @@ public class Introspector {
}
// Check if the MBean has a public constructor
final Constructor[] consList = c.getConstructors();
final Constructor<?>[] consList = c.getConstructors();
if (consList.length == 0) {
throw new NotCompliantMBeanException("MBean class must have public constructor");
}
......@@ -253,7 +253,7 @@ public class Introspector {
* @exception NotCompliantMBeanException The specified class is not a
* JMX compliant MBean
*/
public static MBeanInfo testCompliance(Class baseClass)
public static MBeanInfo testCompliance(Class<?> baseClass)
throws NotCompliantMBeanException {
// ------------------------------
......@@ -267,7 +267,7 @@ public class Introspector {
return testCompliance(baseClass, null);
}
public static void testComplianceMXBeanInterface(Class interfaceClass,
public static void testComplianceMXBeanInterface(Class<?> interfaceClass,
MXBeanMappingFactory factory)
throws NotCompliantMBeanException {
MXBeanIntrospector.getInstance(factory).getAnalyzer(interfaceClass);
......@@ -596,10 +596,10 @@ public class Introspector {
ss[i] = (String) annotationToField(xx[i]);
return ss;
}
if (x instanceof Class)
if (x instanceof Class<?>)
return ((Class<?>) x).getName();
if (x instanceof Enum)
return ((Enum) x).name();
if (x instanceof Enum<?>)
return ((Enum<?>) x).name();
// The only other possibility is that the value is another
// annotation, or that the language has evolved since this code
// was written. We don't allow for either of those currently.
......
......@@ -33,6 +33,7 @@ import java.security.AccessController;
import java.security.Permission;
import java.security.PrivilegedExceptionAction;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.logging.Level;
......@@ -121,7 +122,7 @@ public final class JmxMBeanServer
* {@link javax.management.MBeanServerFactory#newMBeanServer(java.lang.String)}
* instead.
* <p>
* By default, {@link MBeanServerInterceptor} are disabled. Use
* By default, interceptors are disabled. Use
* {@link #JmxMBeanServer(java.lang.String,javax.management.MBeanServer,javax.management.MBeanServerDelegate,boolean)} to enable them.
* </ul>
* @param domain The default domain name used by this MBeanServer.
......@@ -238,7 +239,7 @@ public final class JmxMBeanServer
this.mBeanServerDelegateObject = delegate;
this.outerShell = outer;
final Repository repository = new Repository(domain,fairLock);
final Repository repository = new Repository(domain);
this.mbsInterceptor =
new NamespaceDispatchInterceptor(outer, delegate, instantiator,
repository);
......@@ -1144,7 +1145,7 @@ public final class JmxMBeanServer
// This call requires MBeanPermission 'getClassLoaderRepository'
final ClassLoaderRepository clr = getClassLoaderRepository();
Class theClass;
Class<?> theClass;
try {
if (clr == null) throw new ClassNotFoundException(className);
theClass = clr.loadClass(className);
......@@ -1457,23 +1458,22 @@ public final class JmxMBeanServer
*/
private AttributeList cloneAttributeList(AttributeList list) {
if (list != null) {
List<Attribute> alist = list.asList();
if (!list.getClass().equals(AttributeList.class)) {
// Create new attribute list
//
AttributeList newList = new AttributeList(list.size());
AttributeList newList = new AttributeList(alist.size());
// Iterate through list and replace non JMX attributes
//
for (Iterator i = list.iterator(); i.hasNext(); ) {
Attribute attribute = (Attribute) i.next();
for (Attribute attribute : alist)
newList.add(cloneAttribute(attribute));
}
return newList;
} else {
// Iterate through list and replace non JMX attributes
//
for (int i = 0; i < list.size(); i++) {
Attribute attribute = (Attribute) list.get(i);
for (int i = 0; i < alist.size(); i++) {
Attribute attribute = alist.get(i);
if (!attribute.getClass().equals(Attribute.class)) {
list.set(i, cloneAttribute(attribute));
}
......
......@@ -70,7 +70,7 @@ public class MBeanInstantiator {
* instantiate an MBean of this class in the MBeanServer.
* e.g. it must have a public constructor, be a concrete class...
*/
public void testCreation(Class c) throws NotCompliantMBeanException {
public void testCreation(Class<?> c) throws NotCompliantMBeanException {
Introspector.testCreation(c);
}
......@@ -78,10 +78,10 @@ public class MBeanInstantiator {
* Loads the class with the specified name using this object's
* Default Loader Repository.
**/
public Class findClassWithDefaultLoaderRepository(String className)
public Class<?> findClassWithDefaultLoaderRepository(String className)
throws ReflectionException {
Class theClass;
Class<?> theClass;
if (className == null) {
throw new RuntimeOperationsException(new
IllegalArgumentException("The class name cannot be null"),
......@@ -105,7 +105,7 @@ public class MBeanInstantiator {
* Gets the class for the specified class name using the MBean
* Interceptor's classloader
*/
public Class findClass(String className, ClassLoader loader)
public Class<?> findClass(String className, ClassLoader loader)
throws ReflectionException {
return loadClass(className,loader);
......@@ -115,7 +115,7 @@ public class MBeanInstantiator {
* Gets the class for the specified class name using the specified
* class loader
*/
public Class findClass(String className, ObjectName aLoader)
public Class<?> findClass(String className, ObjectName aLoader)
throws ReflectionException, InstanceNotFoundException {
if (aLoader == null)
......@@ -140,14 +140,14 @@ public class MBeanInstantiator {
* Return an array of Class corresponding to the given signature, using
* the specified class loader.
*/
public Class[] findSignatureClasses(String signature[],
ClassLoader loader)
throws ReflectionException {
public Class<?>[] findSignatureClasses(String signature[],
ClassLoader loader)
throws ReflectionException {
if (signature == null) return null;
final ClassLoader aLoader = loader;
final int length= signature.length;
final Class tab[]=new Class[length];
final Class<?> tab[]=new Class<?>[length];
if (length == 0) return tab;
try {
......@@ -156,7 +156,7 @@ public class MBeanInstantiator {
// forth)
//
final Class primCla = primitiveClasses.get(signature[i]);
final Class<?> primCla = primitiveClasses.get(signature[i]);
if (primCla != null) {
tab[i] = primCla;
continue;
......@@ -203,14 +203,14 @@ public class MBeanInstantiator {
* Instantiates an object given its class, using its empty constructor.
* The call returns a reference to the newly created object.
*/
public Object instantiate(Class theClass)
public Object instantiate(Class<?> theClass)
throws ReflectionException, MBeanException {
Object moi;
// ------------------------------
// ------------------------------
Constructor cons = findConstructor(theClass, null);
Constructor<?> cons = findConstructor(theClass, null);
if (cons == null) {
throw new ReflectionException(new
NoSuchMethodException("No such constructor"));
......@@ -257,14 +257,14 @@ public class MBeanInstantiator {
* signature of its constructor The call returns a reference to
* the newly created object.
*/
public Object instantiate(Class theClass, Object params[],
public Object instantiate(Class<?> theClass, Object params[],
String signature[], ClassLoader loader)
throws ReflectionException, MBeanException {
// Instantiate the new object
// ------------------------------
// ------------------------------
final Class[] tab;
final Class<?>[] tab;
Object moi;
try {
// Build the signature of the method
......@@ -283,7 +283,7 @@ public class MBeanInstantiator {
}
// Query the metadata service to get the right constructor
Constructor cons = findConstructor(theClass, tab);
Constructor<?> cons = findConstructor(theClass, tab);
if (cons == null) {
throw new ReflectionException(new
......@@ -407,7 +407,7 @@ public class MBeanInstantiator {
throw new RuntimeOperationsException(new
IllegalArgumentException(), "Null className passed in parameter");
}
Class theClass;
Class<?> theClass;
if (loaderName == null) {
// Load the class using the agent class loader
theClass = findClass(className, loader);
......@@ -547,7 +547,7 @@ public class MBeanInstantiator {
throws ReflectionException,
MBeanException {
Class theClass = findClassWithDefaultLoaderRepository(className);
Class<?> theClass = findClassWithDefaultLoaderRepository(className);
return instantiate(theClass, params, signature, loader);
}
......@@ -595,7 +595,7 @@ public class MBeanInstantiator {
// ------------------------------
// ------------------------------
Class theClass;
Class<?> theClass;
if (loaderName == null) {
theClass = findClass(className, loader);
......@@ -617,10 +617,10 @@ public class MBeanInstantiator {
* Load a class with the specified loader, or with this object
* class loader if the specified loader is null.
**/
static Class loadClass(String className, ClassLoader loader)
static Class<?> loadClass(String className, ClassLoader loader)
throws ReflectionException {
Class theClass;
Class<?> theClass;
if (className == null) {
throw new RuntimeOperationsException(new
IllegalArgumentException("The class name cannot be null"),
......@@ -647,15 +647,15 @@ public class MBeanInstantiator {
* Load the classes specified in the signature with the given loader,
* or with this object class loader.
**/
static Class[] loadSignatureClasses(String signature[],
ClassLoader loader)
static Class<?>[] loadSignatureClasses(String signature[],
ClassLoader loader)
throws ReflectionException {
if (signature == null) return null;
final ClassLoader aLoader =
(loader==null?MBeanInstantiator.class.getClassLoader():loader);
final int length= signature.length;
final Class tab[]=new Class[length];
final Class<?> tab[]=new Class<?>[length];
if (length == 0) return tab;
try {
......@@ -664,7 +664,7 @@ public class MBeanInstantiator {
// forth)
//
final Class primCla = primitiveClasses.get(signature[i]);
final Class<?> primCla = primitiveClasses.get(signature[i]);
if (primCla != null) {
tab[i] = primCla;
continue;
......@@ -710,9 +710,9 @@ public class MBeanInstantiator {
private static final Map<String, Class<?>> primitiveClasses = Util.newMap();
static {
for (Class<?> c : new Class[] {byte.class, short.class, int.class,
long.class, float.class, double.class,
char.class, boolean.class})
for (Class<?> c : new Class<?>[] {byte.class, short.class, int.class,
long.class, float.class, double.class,
char.class, boolean.class})
primitiveClasses.put(c.getName(), c);
}
}
......@@ -160,7 +160,7 @@ class MXBeanIntrospector extends MBeanIntrospector<ConvertingMethod> {
// matched to the corresponding Java type, except when that
// type is primitive.
Type t = m.getGenericParameterTypes()[paramNo];
return (!(t instanceof Class) || !((Class) t).isPrimitive());
return (!(t instanceof Class<?>) || !((Class<?>) t).isPrimitive());
} else {
Object v;
try {
......@@ -354,7 +354,7 @@ class MXBeanIntrospector extends MBeanIntrospector<ConvertingMethod> {
}
}
private static Descriptor typeDescriptor(OpenType openType,
private static Descriptor typeDescriptor(OpenType<?> openType,
Type originalType) {
return new ImmutableDescriptor(
new String[] {"openType",
......@@ -380,37 +380,37 @@ class MXBeanIntrospector extends MBeanIntrospector<ConvertingMethod> {
if (type instanceof GenericArrayType) {
return canUseOpenInfo(
((GenericArrayType) type).getGenericComponentType());
} else if (type instanceof Class && ((Class<?>) type).isArray()) {
} else if (type instanceof Class<?> && ((Class<?>) type).isArray()) {
return canUseOpenInfo(
((Class<?>) type).getComponentType());
}
return (!(type instanceof Class && ((Class<?>) type).isPrimitive()));
return (!(type instanceof Class<?> && ((Class<?>) type).isPrimitive()));
}
private static String originalTypeString(Type type) {
if (type instanceof Class)
return ((Class) type).getName();
if (type instanceof Class<?>)
return ((Class<?>) type).getName();
else
return genericTypeString(type);
return typeName(type);
}
private static String genericTypeString(Type type) {
static String typeName(Type type) {
if (type instanceof Class<?>) {
Class<?> c = (Class<?>) type;
if (c.isArray())
return genericTypeString(c.getComponentType()) + "[]";
return typeName(c.getComponentType()) + "[]";
else
return c.getName();
} else if (type instanceof GenericArrayType) {
GenericArrayType gat = (GenericArrayType) type;
return genericTypeString(gat.getGenericComponentType()) + "[]";
return typeName(gat.getGenericComponentType()) + "[]";
} else if (type instanceof ParameterizedType) {
ParameterizedType pt = (ParameterizedType) type;
StringBuilder sb = new StringBuilder();
sb.append(genericTypeString(pt.getRawType())).append("<");
sb.append(typeName(pt.getRawType())).append("<");
String sep = "";
for (Type t : pt.getActualTypeArguments()) {
sb.append(sep).append(genericTypeString(t));
sb.append(sep).append(typeName(t));
sep = ", ";
}
return sb.append(">").toString();
......
......@@ -54,7 +54,8 @@ class ObjectInputStreamWithLoader extends ObjectInputStream {
this.loader = theLoader;
}
protected Class resolveClass(ObjectStreamClass aClass)
@Override
protected Class<?> resolveClass(ObjectStreamClass aClass)
throws IOException, ClassNotFoundException {
if (loader == null) {
return super.resolveClass(aClass);
......
......@@ -47,16 +47,16 @@ final class SecureClassLoaderRepository
public SecureClassLoaderRepository(ClassLoaderRepository clr) {
this.clr=clr;
}
public final Class loadClass(String className)
public final Class<?> loadClass(String className)
throws ClassNotFoundException {
return clr.loadClass(className);
}
public final Class loadClassWithout(ClassLoader loader,
public final Class<?> loadClassWithout(ClassLoader loader,
String className)
throws ClassNotFoundException {
return clr.loadClassWithout(loader,className);
}
public final Class loadClassBefore(ClassLoader loader,
public final Class<?> loadClassBefore(ClassLoader loader,
String className)
throws ClassNotFoundException {
return clr.loadClassBefore(loader,className);
......
......@@ -669,7 +669,7 @@ public class Util {
}
public static <T> Set<T> cloneSet(Set<T> set) {
if (set instanceof SortedSet) {
if (set instanceof SortedSet<?>) {
@SuppressWarnings("unchecked")
SortedSet<T> sset = (SortedSet<T>) set;
set = new TreeSet<T>(sset.comparator());
......@@ -680,7 +680,7 @@ public class Util {
}
public static <T> Set<T> equivalentEmptySet(Set<T> set) {
if (set instanceof SortedSet) {
if (set instanceof SortedSet<?>) {
@SuppressWarnings("unchecked")
SortedSet<T> sset = (SortedSet<T>) set;
set = new TreeSet<T>(sset.comparator());
......
......@@ -118,9 +118,9 @@ class WeakIdentityHashMap<K, V> {
public boolean equals(Object o) {
if (this == o)
return true;
if (!(o instanceof IdentityWeakReference))
if (!(o instanceof IdentityWeakReference<?>))
return false;
IdentityWeakReference wr = (IdentityWeakReference) o;
IdentityWeakReference<?> wr = (IdentityWeakReference<?>) o;
Object got = get();
return (got != null && got == wr.get());
}
......
/*
* Copyright 2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package com.sun.jmx.namespace;
import com.sun.jmx.defaults.JmxProperties;
import java.io.IOException;
import java.util.Collections;
import java.util.Map;
import java.util.WeakHashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.management.ListenerNotFoundException;
import javax.management.MBeanServerConnection;
import javax.management.NotificationFilter;
import javax.management.NotificationListener;
import javax.management.event.EventClient;
import javax.management.event.EventClientDelegateMBean;
import javax.management.namespace.JMXNamespace;
import javax.management.namespace.JMXNamespaces;
import javax.management.remote.JMXAddressable;
import javax.management.remote.JMXConnector;
import javax.management.remote.JMXServiceURL;
import javax.security.auth.Subject;
/**
* A collection of methods that provide JMXConnector wrappers for
* JMXRemoteNamepaces underlying connectors.
* <p><b>
* This API is a Sun internal API and is subject to changes without notice.
* </b></p>
* @since 1.7
*/
public final class JMXNamespaceUtils {
/**
* A logger for this class.
**/
private static final Logger LOG = JmxProperties.NAMESPACE_LOGGER;
private static <K,V> Map<K,V> newWeakHashMap() {
return new WeakHashMap<K,V>();
}
/** There are no instances of this class */
private JMXNamespaceUtils() {
}
// returns un unmodifiable view of a map.
public static <K,V> Map<K,V> unmodifiableMap(Map<K,V> aMap) {
if (aMap == null || aMap.isEmpty())
return Collections.emptyMap();
return Collections.unmodifiableMap(aMap);
}
/**
* A base class that helps writing JMXConnectors that return
* MBeanServerConnection wrappers.
* This base class wraps an inner JMXConnector (the source), and preserve
* its caching policy. If a connection is cached in the source, its wrapper
* will be cached in this connector too.
* Author's note: rewriting this with java.lang.reflect.Proxy could be
* envisaged. It would avoid the combinatory sub-classing introduced by
* JMXAddressable.
* <p>
* Note: all the standard JMXConnector implementations are serializable.
* This implementation here is not. Should it be?
* I believe it must not be serializable unless it becomes
* part of a public API (either standard or officially exposed
* and supported in a documented com.sun package)
**/
static class JMXCachingConnector
implements JMXConnector {
// private static final long serialVersionUID = -2279076110599707875L;
final JMXConnector source;
// if this object is made serializable, then the variable below
// needs to become volatile transient and be lazyly-created...
private final
Map<MBeanServerConnection,MBeanServerConnection> connectionMap;
public JMXCachingConnector(JMXConnector source) {
this.source = checkNonNull(source, "source");
connectionMap = newWeakHashMap();
}
private MBeanServerConnection
getCached(MBeanServerConnection inner) {
return connectionMap.get(inner);
}
private MBeanServerConnection putCached(final MBeanServerConnection inner,
final MBeanServerConnection wrapper) {
if (inner == wrapper) return wrapper;
synchronized (this) {
final MBeanServerConnection concurrent =
connectionMap.get(inner);
if (concurrent != null) return concurrent;
connectionMap.put(inner,wrapper);
}
return wrapper;
}
public void addConnectionNotificationListener(NotificationListener
listener, NotificationFilter filter, Object handback) {
source.addConnectionNotificationListener(listener,filter,handback);
}
public void close() throws IOException {
source.close();
}
public void connect() throws IOException {
source.connect();
}
public void connect(Map<String,?> env) throws IOException {
source.connect(env);
}
public String getConnectionId() throws IOException {
return source.getConnectionId();
}
/**
* Preserve caching policy of the underlying connector.
**/
public MBeanServerConnection
getMBeanServerConnection() throws IOException {
final MBeanServerConnection inner =
source.getMBeanServerConnection();
final MBeanServerConnection cached = getCached(inner);
if (cached != null) return cached;
final MBeanServerConnection wrapper = wrap(inner);
return putCached(inner,wrapper);
}
public MBeanServerConnection
getMBeanServerConnection(Subject delegationSubject)
throws IOException {
final MBeanServerConnection wrapped =
source.getMBeanServerConnection(delegationSubject);
synchronized (this) {
final MBeanServerConnection cached = getCached(wrapped);
if (cached != null) return cached;
final MBeanServerConnection wrapper =
wrapWithSubject(wrapped,delegationSubject);
return putCached(wrapped,wrapper);
}
}
public void removeConnectionNotificationListener(
NotificationListener listener)
throws ListenerNotFoundException {
source.removeConnectionNotificationListener(listener);
}
public void removeConnectionNotificationListener(
NotificationListener l, NotificationFilter f,
Object handback) throws ListenerNotFoundException {
source.removeConnectionNotificationListener(l,f,handback);
}
/**
* This is the method that subclass will redefine. This method
* is called by {@code this.getMBeanServerConnection()}.
* {@code inner} is the connection returned by
* {@code source.getMBeanServerConnection()}.
**/
protected MBeanServerConnection wrap(MBeanServerConnection inner)
throws IOException {
return inner;
}
/**
* Subclass may also want to redefine this method.
* By default it calls wrap(inner). This method
* is called by {@code this.getMBeanServerConnection(Subject)}.
* {@code inner} is the connection returned by
* {@code source.getMBeanServerConnection(Subject)}.
**/
protected MBeanServerConnection wrapWithSubject(
MBeanServerConnection inner, Subject delegationSubject)
throws IOException {
return wrap(inner);
}
@Override
public String toString() {
if (source instanceof JMXAddressable) {
final JMXServiceURL address =
((JMXAddressable)source).getAddress();
if (address != null)
return address.toString();
}
return source.toString();
}
}
/**
* The name space connector can do 'cd'
**/
static class JMXNamespaceConnector extends JMXCachingConnector {
// private static final long serialVersionUID = -4813611540843020867L;
private final String toDir;
private final boolean closeable;
public JMXNamespaceConnector(JMXConnector source, String toDir,
boolean closeable) {
super(source);
this.toDir = toDir;
this.closeable = closeable;
}
@Override
public void close() throws IOException {
if (!closeable)
throw new UnsupportedOperationException("close");
else super.close();
}
@Override
protected MBeanServerConnection wrap(MBeanServerConnection wrapped)
throws IOException {
if (LOG.isLoggable(Level.FINER))
LOG.finer("Creating name space proxy connection for source: "+
"namespace="+toDir);
return JMXNamespaces.narrowToNamespace(wrapped,toDir);
}
@Override
public String toString() {
return "JMXNamespaces.narrowToNamespace("+
super.toString()+
", \""+toDir+"\")";
}
}
static class JMXEventConnector extends JMXCachingConnector {
// private static final long serialVersionUID = 4742659236340242785L;
JMXEventConnector(JMXConnector wrapped) {
super(wrapped);
}
@Override
protected MBeanServerConnection wrap(MBeanServerConnection inner)
throws IOException {
return EventClient.getEventClientConnection(inner);
}
@Override
public String toString() {
return "EventClient.withEventClient("+super.toString()+")";
}
}
static class JMXAddressableEventConnector extends JMXEventConnector
implements JMXAddressable {
// private static final long serialVersionUID = -9128520234812124712L;
JMXAddressableEventConnector(JMXConnector wrapped) {
super(wrapped);
}
public JMXServiceURL getAddress() {
return ((JMXAddressable)source).getAddress();
}
}
/**
* Creates a connector whose MBeamServerConnection will point to the
* given sub name space inside the source connector.
* @see JMXNamespace
**/
public static JMXConnector cd(final JMXConnector source,
final String toNamespace,
final boolean closeable)
throws IOException {
checkNonNull(source, "JMXConnector");
if (toNamespace == null || toNamespace.equals(""))
return source;
return new JMXNamespaceConnector(source,toNamespace,closeable);
}
/**
* Returns a JMX Connector that will use an {@link EventClient}
* to subscribe for notifications. If the server doesn't have
* an {@link EventClientDelegateMBean}, then the connector will
* use the legacy notification mechanism instead.
*
* @param source The underlying JMX Connector wrapped by the returned
* connector.
* @return A JMX Connector that will uses an {@link EventClient}, if
* available.
* @see EventClient#getEventClientConnection(MBeanServerConnection)
*/
public static JMXConnector withEventClient(final JMXConnector source) {
checkNonNull(source, "JMXConnector");
if (source instanceof JMXAddressable)
return new JMXAddressableEventConnector(source);
else
return new JMXEventConnector(source);
}
public static <T> T checkNonNull(T parameter, String name) {
if (parameter == null)
throw new IllegalArgumentException(name+" must not be null");
return parameter;
}
}
......@@ -49,11 +49,6 @@ public class ObjectNameRouter {
final int tlen;
final boolean identity;
public ObjectNameRouter(String targetDirName) {
this(targetDirName,null);
}
/** Creates a new instance of ObjectNameRouter */
public ObjectNameRouter(final String remove, final String add) {
this.targetPrefix = (remove==null?"":remove);
......@@ -186,6 +181,4 @@ public class ObjectNameRouter {
b.append(NAMESPACE_SEPARATOR);
return b.toString();
}
}
......@@ -31,7 +31,6 @@ import java.util.logging.Level;
import java.util.logging.Logger;
import javax.management.MBeanServerConnection;
import javax.management.namespace.JMXNamespaces;
/**
......@@ -57,22 +56,14 @@ public class RoutingConnectionProxy
private static final Logger LOG = JmxProperties.NAMESPACE_LOGGER;
/**
* Creates a new instance of RoutingConnectionProxy
*/
public RoutingConnectionProxy(MBeanServerConnection source,
String sourceDir) {
this(source,sourceDir,"",false);
}
/**
* Creates a new instance of RoutingConnectionProxy
*/
public RoutingConnectionProxy(MBeanServerConnection source,
String sourceDir,
String targetDir,
boolean forwardsContext) {
super(source,sourceDir,targetDir,forwardsContext);
boolean probe) {
super(source, sourceDir, targetDir, probe);
if (LOG.isLoggable(Level.FINER))
LOG.finer("RoutingConnectionProxy for " + getSourceNamespace() +
......@@ -85,15 +76,13 @@ public class RoutingConnectionProxy
final String sourceNs = getSourceNamespace();
String wrapped = String.valueOf(source());
if ("".equals(targetNs)) {
if (forwardsContext)
wrapped = "ClientContext.withDynamicContext("+wrapped+")";
return "JMXNamespaces.narrowToNamespace("+
wrapped+", \""+
sourceNs+"\")";
}
return this.getClass().getSimpleName()+"("+wrapped+", \""+
sourceNs+"\", \""+
targetNs+"\", "+forwardsContext+")";
targetNs+"\")";
}
static final RoutingProxyFactory
......@@ -102,22 +91,16 @@ public class RoutingConnectionProxy
<MBeanServerConnection,RoutingConnectionProxy>() {
public RoutingConnectionProxy newInstance(MBeanServerConnection source,
String sourcePath, String targetPath,
boolean forwardsContext) {
String sourcePath, String targetPath, boolean probe) {
return new RoutingConnectionProxy(source,sourcePath,
targetPath,forwardsContext);
}
public RoutingConnectionProxy newInstance(
MBeanServerConnection source, String sourcePath) {
return new RoutingConnectionProxy(source,sourcePath);
targetPath, probe);
}
};
public static MBeanServerConnection cd(MBeanServerConnection source,
String sourcePath) {
public static MBeanServerConnection cd(
MBeanServerConnection source, String sourcePath, boolean probe) {
return RoutingProxy.cd(RoutingConnectionProxy.class, FACTORY,
source, sourcePath);
source, sourcePath, probe);
}
}
......@@ -30,6 +30,7 @@ import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.management.InstanceNotFoundException;
import javax.management.MBeanException;
import javax.management.MBeanRegistrationException;
......@@ -90,17 +91,9 @@ import javax.management.namespace.JMXNamespaces;
// targetNs=<encoded-context> // context must be removed from object name
// sourceNs="" // nothing to add...
//
// RoutingProxies can also be used on the client side to implement
// "withClientContext" operations. In that case, the boolean parameter
// 'forwards context' is set to true, targetNs is "", and sourceNS may
// also be "". When forwardsContext is true, the RoutingProxy dynamically
// creates an ObjectNameRouter for each operation - in order to dynamically add
// the context attached to the thread to the routing ObjectName. This is
// performed in the getObjectNameRouter() method.
//
// Finally, in order to avoid too many layers of wrapping,
// RoutingConnectionProxy and RoutingServerProxy can be created through a
// factory method that can concatenate namespace pathes in order to
// factory method that can concatenate namespace paths in order to
// return a single RoutingProxy - rather than wrapping a RoutingProxy inside
// another RoutingProxy. See RoutingConnectionProxy.cd and
// RoutingServerProxy.cd
......@@ -146,25 +139,27 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
private final T source;
// The name space we're narrowing to (usually some name space in
// the source MBeanServerConnection
// the source MBeanServerConnection), e.g. "a" for the namespace
// "a//". This is empty in the case of ClientContext described above.
private final String sourceNs;
// The name space we pretend to be mounted in (usually "")
// The name space we pretend to be mounted in. This is empty except
// in the case of ClientContext described above (where it will be
// something like "jmx.context//foo=bar".
private final String targetNs;
// The name of the JMXNamespace that handles the source name space
private final ObjectName handlerName;
private final ObjectNameRouter router;
final boolean forwardsContext;
private volatile String defaultDomain = null;
/**
* Creates a new instance of RoutingProxy
*/
protected RoutingProxy(T source,
String sourceNs,
String targetNs,
boolean forwardsContext) {
String sourceNs,
String targetNs,
boolean probe) {
if (source == null) throw new IllegalArgumentException("null");
this.sourceNs = JMXNamespaces.normalizeNamespaceName(sourceNs);
......@@ -177,13 +172,17 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
// System.err.println("sourceNs: "+sourceNs);
this.handlerName =
JMXNamespaces.getNamespaceObjectName(this.sourceNs);
try {
// System.err.println("handlerName: "+handlerName);
if (!source.isRegistered(handlerName))
throw new IllegalArgumentException(sourceNs +
": no such name space");
} catch (IOException x) {
throw new IllegalArgumentException("source stale: "+x,x);
if (probe) {
try {
if (!source.isRegistered(handlerName)) {
InstanceNotFoundException infe =
new InstanceNotFoundException(handlerName);
throw new IllegalArgumentException(sourceNs +
": no such name space", infe);
}
} catch (IOException x) {
throw new IllegalArgumentException("source stale: "+x,x);
}
}
}
this.source = source;
......@@ -191,7 +190,6 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
JMXNamespaces.normalizeNamespaceName(targetNs));
this.router =
new ObjectNameRouter(this.targetNs,this.sourceNs);
this.forwardsContext = forwardsContext;
if (LOG.isLoggable(Level.FINER))
LOG.finer("RoutingProxy for " + this.sourceNs + " created");
......@@ -200,14 +198,6 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
@Override
public T source() { return source; }
ObjectNameRouter getObjectNameRouter() {
// TODO: uncomment this when contexts are added
// if (forwardsContext)
// return ObjectNameRouter.wrapWithContext(router);
// else
return router;
}
@Override
public ObjectName toSource(ObjectName targetName)
throws MalformedObjectNameException {
......@@ -222,8 +212,7 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
if (defaultDomain != null)
targetName = targetName.withDomain(defaultDomain);
}
final ObjectNameRouter r = getObjectNameRouter();
return r.toSourceContext(targetName,true);
return router.toSourceContext(targetName,true);
}
@Override
......@@ -243,8 +232,7 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
public ObjectName toTarget(ObjectName sourceName)
throws MalformedObjectNameException {
if (sourceName == null) return null;
final ObjectNameRouter r = getObjectNameRouter();
return r.toTargetContext(sourceName,false);
return router.toTargetContext(sourceName,false);
}
private Object getAttributeFromHandler(String attributeName)
......@@ -357,11 +345,8 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
// instance.
static interface RoutingProxyFactory<T extends MBeanServerConnection,
R extends RoutingProxy<T>> {
R newInstance(T source,
String sourcePath, String targetPath,
boolean forwardsContext);
R newInstance(T source,
String sourcePath);
public R newInstance(
T source, String sourcePath, String targetPath, boolean probe);
}
// Performs a narrowDownToNamespace operation.
......@@ -377,7 +362,7 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
static <T extends MBeanServerConnection, R extends RoutingProxy<T>>
R cd(Class<R> routingProxyClass,
RoutingProxyFactory<T,R> factory,
T source, String sourcePath) {
T source, String sourcePath, boolean probe) {
if (source == null) throw new IllegalArgumentException("null");
if (source.getClass().equals(routingProxyClass)) {
// cast is OK here, but findbugs complains unless we use class.cast
......@@ -400,14 +385,13 @@ public abstract class RoutingProxy<T extends MBeanServerConnection>
final String path =
JMXNamespaces.concat(other.getSourceNamespace(),
sourcePath);
return factory.newInstance(other.source(),path,"",
other.forwardsContext);
return factory.newInstance(other.source(), path, "", probe);
}
// Note: we could do possibly something here - but it would involve
// removing part of targetDir, and possibly adding
// something to sourcePath.
// Too complex to bother! => simply default to stacking...
}
return factory.newInstance(source,sourcePath);
return factory.newInstance(source, sourcePath, "", probe);
}
}
......@@ -54,7 +54,6 @@ import javax.management.OperationsException;
import javax.management.QueryExp;
import javax.management.ReflectionException;
import javax.management.loading.ClassLoaderRepository;
import javax.management.namespace.JMXNamespaces;
/**
* A RoutingServerProxy is an MBeanServer proxy that proxies a
......@@ -76,19 +75,11 @@ public class RoutingServerProxy
extends RoutingProxy<MBeanServer>
implements MBeanServer {
/**
* Creates a new instance of RoutingServerProxy
*/
public RoutingServerProxy(MBeanServer source,
String sourceNs) {
this(source,sourceNs,"",false);
}
public RoutingServerProxy(MBeanServer source,
String sourceNs,
String targetNs,
boolean forwardsContext) {
super(source,sourceNs,targetNs,forwardsContext);
boolean probe) {
super(source, sourceNs, targetNs, probe);
}
/**
......@@ -571,20 +562,15 @@ public class RoutingServerProxy
FACTORY = new RoutingProxyFactory<MBeanServer,RoutingServerProxy>() {
public RoutingServerProxy newInstance(MBeanServer source,
String sourcePath, String targetPath,
boolean forwardsContext) {
return new RoutingServerProxy(source,sourcePath,
targetPath,forwardsContext);
}
public RoutingServerProxy newInstance(
MBeanServer source, String sourcePath) {
return new RoutingServerProxy(source,sourcePath);
String sourcePath, String targetPath, boolean probe) {
return new RoutingServerProxy(
source, sourcePath, targetPath, probe);
}
};
public static MBeanServer cd(MBeanServer source, String sourcePath) {
public static MBeanServer cd(
MBeanServer source, String sourcePath, boolean probe) {
return RoutingProxy.cd(RoutingServerProxy.class, FACTORY,
source, sourcePath);
source, sourcePath, probe);
}
}
......@@ -120,7 +120,7 @@ public class ArrayNotificationBuffer implements NotificationBuffer {
private final Collection<ShareBuffer> sharers = new HashSet<ShareBuffer>(1);
public static NotificationBuffer getNotificationBuffer(
MBeanServer mbs, Map env) {
MBeanServer mbs, Map<String, ?> env) {
if (env == null)
env = Collections.emptyMap();
......
......@@ -54,7 +54,7 @@ import com.sun.jmx.remote.util.EnvHelp;
public abstract class ClientNotifForwarder {
public ClientNotifForwarder(Map env) {
public ClientNotifForwarder(Map<String, ?> env) {
this(null, env);
}
......@@ -113,7 +113,7 @@ public abstract class ClientNotifForwarder {
private Thread thread;
}
public ClientNotifForwarder(ClassLoader defaultClassLoader, Map env) {
public ClientNotifForwarder(ClassLoader defaultClassLoader, Map<String, ?> env) {
maxNotifications = EnvHelp.getMaxFetchNotifNumber(env);
timeout = EnvHelp.getFetchTimeout(env);
......
......@@ -36,7 +36,7 @@ import org.omg.CORBA.ORB;
import org.omg.CORBA.TypeCode;
import org.omg.CORBA.portable.BoxedValueHelper;
@SuppressWarnings("deprecation")
@SuppressWarnings({"deprecation", "rawtypes"})
public class ProxyInputStream extends org.omg.CORBA_2_3.portable.InputStream {
public ProxyInputStream(org.omg.CORBA.portable.InputStream in) {
this.in = in;
......
......@@ -59,7 +59,7 @@ public class ServerNotifForwarder {
public ServerNotifForwarder(MBeanServer mbeanServer,
Map env,
Map<String, ?> env,
NotificationBuffer notifBuffer,
String connectionId) {
this.mbeanServer = mbeanServer;
......
......@@ -29,6 +29,6 @@ import java.io.IOException;
import java.rmi.MarshalledObject;
public interface Unmarshal {
public Object get(MarshalledObject mo)
public Object get(MarshalledObject<?> mo)
throws IOException, ClassNotFoundException;
}
......@@ -26,6 +26,7 @@
package com.sun.jmx.remote.security;
import com.sun.jmx.mbeanserver.GetPropertyAction;
import com.sun.jmx.mbeanserver.Util;
import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
......@@ -146,8 +147,8 @@ public class FileLoginModule implements LoginModule {
// Initial state
private Subject subject;
private CallbackHandler callbackHandler;
private Map<String, ?> sharedState;
private Map options;
private Map<String, Object> sharedState;
private Map<String, ?> options;
private String passwordFile;
private String passwordFileDisplayName;
private boolean userSuppliedPasswordFile;
......@@ -172,7 +173,7 @@ public class FileLoginModule implements LoginModule {
this.subject = subject;
this.callbackHandler = callbackHandler;
this.sharedState = sharedState;
this.sharedState = Util.cast(sharedState);
this.options = options;
// initialize any configured options
......@@ -454,8 +455,8 @@ public class FileLoginModule implements LoginModule {
if (storePass &&
!sharedState.containsKey(USERNAME_KEY) &&
!sharedState.containsKey(PASSWORD_KEY)) {
((Map) sharedState).put(USERNAME_KEY, username);
((Map) sharedState).put(PASSWORD_KEY, password);
sharedState.put(USERNAME_KEY, username);
sharedState.put(PASSWORD_KEY, password);
}
// Create a new user principal
......
......@@ -87,7 +87,7 @@ public final class JMXPluggableAuthenticator implements JMXAuthenticator {
* @exception SecurityException if the authentication mechanism cannot be
* initialized.
*/
public JMXPluggableAuthenticator(Map env) {
public JMXPluggableAuthenticator(Map<?, ?> env) {
String loginConfigName = null;
String passwordFile = null;
......
......@@ -249,9 +249,8 @@ public class MBeanServerFileAccessController
}
});
if (s == null) return; /* security has not been enabled */
final Set principals = s.getPrincipals();
for (Iterator i = principals.iterator(); i.hasNext(); ) {
final Principal p = (Principal) i.next();
final Set<Principal> principals = s.getPrincipals();
for (Principal p : principals) {
String grantedAccessLevel;
synchronized (props) {
grantedAccessLevel = props.getProperty(p.getName());
......@@ -271,8 +270,8 @@ public class MBeanServerFileAccessController
}
private void checkValues(Properties props) {
Collection c = props.values();
for (Iterator i = c.iterator(); i.hasNext(); ) {
Collection<?> c = props.values();
for (Iterator<?> i = c.iterator(); i.hasNext(); ) {
final String accessLevel = (String) i.next();
if (!accessLevel.equals(READONLY) &&
!accessLevel.equals(READWRITE)) {
......
......@@ -38,7 +38,7 @@ public class ClassLoaderWithRepository extends ClassLoader {
this.cl2 = cl2;
}
protected Class findClass(String name) throws ClassNotFoundException {
protected Class<?> findClass(String name) throws ClassNotFoundException {
try {
return repository.loadClass(name);
} catch (ClassNotFoundException cne) {
......
......@@ -41,7 +41,7 @@ public class ClassLogger {
people to use at least J2SE 1.4. */
boolean loaded = false;
try {
Class c = java.util.logging.Logger.class;
Class<?> c = java.util.logging.Logger.class;
loaded = true;
} catch (Error e) {
// OK.
......
......@@ -117,7 +117,7 @@ public class EnvHelp {
* <code>jmx.remote.default.class.loader.name</code> is specified
* and the ClassLoader MBean is not found in <var>mbs</var>.
*/
public static ClassLoader resolveServerClassLoader(Map env,
public static ClassLoader resolveServerClassLoader(Map<String, ?> env,
MBeanServer mbs)
throws InstanceNotFoundException {
......@@ -194,7 +194,7 @@ public class EnvHelp {
* <code>jmx.remote.default.class.loader</code> is specified
* and is not an instance of {@link ClassLoader}.
*/
public static ClassLoader resolveClientClassLoader(Map env) {
public static ClassLoader resolveClientClassLoader(Map<String, ?> env) {
if (env == null)
return Thread.currentThread().getContextClassLoader();
......@@ -241,7 +241,7 @@ public class EnvHelp {
try {
java.lang.reflect.Method getCause =
t.getClass().getMethod("getCause", (Class[]) null);
t.getClass().getMethod("getCause", (Class<?>[]) null);
ret = (Throwable)getCause.invoke(t, (Object[]) null);
} catch (Exception e) {
......@@ -264,7 +264,7 @@ public class EnvHelp {
* Returns the size of a notification buffer for a connector server.
* The default value is 1000.
*/
public static int getNotifBufferSize(Map env) {
public static int getNotifBufferSize(Map<String, ?> env) {
int defaultQueueSize = 1000; // default value
// keep it for the compability for the fix:
......@@ -327,7 +327,7 @@ public class EnvHelp {
* Returns the maximum notification number which a client will
* fetch every time.
*/
public static int getMaxFetchNotifNumber(Map env) {
public static int getMaxFetchNotifNumber(Map<String, ?> env) {
return (int) getIntegerAttribute(env, MAX_FETCH_NOTIFS, 1000, 1,
Integer.MAX_VALUE);
}
......@@ -344,7 +344,7 @@ public class EnvHelp {
/**
* Returns the timeout for a client to fetch notifications.
*/
public static long getFetchTimeout(Map env) {
public static long getFetchTimeout(Map<String, ?> env) {
return getIntegerAttribute(env, FETCH_TIMEOUT, 60000L, 0,
Long.MAX_VALUE);
}
......@@ -361,7 +361,7 @@ public class EnvHelp {
"com.sun.jmx.remote.notification.access.controller";
public static NotificationAccessController getNotificationAccessController(
Map env) {
Map<String, ?> env) {
return (env == null) ? null :
(NotificationAccessController) env.get(NOTIF_ACCESS_CONTROLLER);
}
......@@ -378,7 +378,7 @@ public class EnvHelp {
* an entry for <code>name</code> but it does not meet the
* constraints above.
*/
public static long getIntegerAttribute(Map env, String name,
public static long getIntegerAttribute(Map<String, ?> env, String name,
long defaultValue, long minValue,
long maxValue) {
final Object o;
......@@ -421,9 +421,8 @@ public class EnvHelp {
/* Check that all attributes have a key that is a String.
Could make further checks, e.g. appropriate types for attributes. */
public static void checkAttributes(Map attributes) {
for (Iterator it = attributes.keySet().iterator(); it.hasNext(); ) {
Object key = it.next();
public static void checkAttributes(Map<?, ?> attributes) {
for (Object key : attributes.keySet()) {
if (!(key instanceof String)) {
final String msg =
"Attributes contain key that is not a string: " + key;
......@@ -455,7 +454,7 @@ public class EnvHelp {
logger.trace("purgeUnserializable", "starts");
ObjectOutputStream oos = null;
int i = 0;
for (Iterator it = objects.iterator(); it.hasNext(); i++) {
for (Iterator<?> it = objects.iterator(); it.hasNext(); i++) {
Object v = it.next();
if (v == null || v instanceof String) {
......@@ -564,18 +563,18 @@ public class EnvHelp {
guarantees that we will never call next() on the corresponding
iterator. */
String sentinelKey = map.lastKey() + "X";
Iterator keyIterator = map.keySet().iterator();
Iterator stringIterator = hiddenStrings.iterator();
Iterator prefixIterator = hiddenPrefixes.iterator();
Iterator<String> keyIterator = map.keySet().iterator();
Iterator<String> stringIterator = hiddenStrings.iterator();
Iterator<String> prefixIterator = hiddenPrefixes.iterator();
String nextString;
if (stringIterator.hasNext())
nextString = (String) stringIterator.next();
nextString = stringIterator.next();
else
nextString = sentinelKey;
String nextPrefix;
if (prefixIterator.hasNext())
nextPrefix = (String) prefixIterator.next();
nextPrefix = prefixIterator.next();
else
nextPrefix = sentinelKey;
......@@ -583,7 +582,7 @@ public class EnvHelp {
or prefix, remove it. */
keys:
while (keyIterator.hasNext()) {
String key = (String) keyIterator.next();
String key = keyIterator.next();
/* Continue through string-match values until we find one
that is either greater than the current key, or equal
......@@ -591,7 +590,7 @@ public class EnvHelp {
int cmp = +1;
while ((cmp = nextString.compareTo(key)) < 0) {
if (stringIterator.hasNext())
nextString = (String) stringIterator.next();
nextString = stringIterator.next();
else
nextString = sentinelKey;
}
......@@ -609,7 +608,7 @@ public class EnvHelp {
continue keys;
}
if (prefixIterator.hasNext())
nextPrefix = (String) prefixIterator.next();
nextPrefix = prefixIterator.next();
else
nextPrefix = sentinelKey;
}
......@@ -640,7 +639,7 @@ public class EnvHelp {
/**
* Returns the server side connection timeout.
*/
public static long getServerConnectionTimeout(Map env) {
public static long getServerConnectionTimeout(Map<String, ?> env) {
return getIntegerAttribute(env, SERVER_CONNECTION_TIMEOUT, 120000L,
0, Long.MAX_VALUE);
}
......@@ -656,7 +655,7 @@ public class EnvHelp {
/**
* Returns the client connection check period.
*/
public static long getConnectionCheckPeriod(Map env) {
public static long getConnectionCheckPeriod(Map<String, ?> env) {
return getIntegerAttribute(env, CLIENT_CONNECTION_CHECK_PERIOD, 60000L,
0, Long.MAX_VALUE);
}
......@@ -691,7 +690,7 @@ public class EnvHelp {
* to {@code String}.
*/
public static boolean computeBooleanFromString(
Map env, String prop, boolean systemProperty) {
Map<String, ?> env, String prop, boolean systemProperty) {
if (env == null)
throw new IllegalArgumentException("env map cannot be null");
......@@ -744,7 +743,8 @@ public class EnvHelp {
* to {@code String}.
*/
public static boolean computeBooleanFromString(
Map env, String prop, boolean systemProperty, boolean defaultValue) {
Map<String, ?> env, String prop,
boolean systemProperty, boolean defaultValue) {
if (env == null)
throw new IllegalArgumentException("env map cannot be null");
......@@ -774,7 +774,7 @@ public class EnvHelp {
public static <K, V> Hashtable<K, V> mapToHashtable(Map<K, V> map) {
HashMap<K, V> m = new HashMap<K, V>(map);
if (m.containsKey(null)) m.remove(null);
for (Iterator i = m.values().iterator(); i.hasNext(); )
for (Iterator<?> i = m.values().iterator(); i.hasNext(); )
if (i.next() == null) i.remove();
return new Hashtable<K, V>(m);
}
......@@ -783,7 +783,7 @@ public class EnvHelp {
* Returns true if the parameter JMXConnector.USE_EVENT_SERVICE is set to a
* String equals "true" by ignoring case in the map or in the System.
*/
public static boolean eventServiceEnabled(Map env) {
public static boolean eventServiceEnabled(Map<String, ?> env) {
return computeBooleanFromString(env, JMXConnector.USE_EVENT_SERVICE, true);
}
......@@ -793,7 +793,7 @@ public class EnvHelp {
* If the property DELEGATE_TO_EVENT_SERVICE is not set, returns
* a default value of "true".
*/
public static boolean delegateToEventService(Map env) {
public static boolean delegateToEventService(Map<String, ?> env) {
return computeBooleanFromString(env,
JMXConnectorServer.DELEGATE_TO_EVENT_SERVICE, true, true);
}
......
......@@ -138,8 +138,8 @@ public class EventClientConnection implements InvocationHandler,
Class<T> interfaceClass, Callable<EventClient> eventClientFactory) {
final InvocationHandler handler =
new EventClientConnection(connection,eventClientFactory);
final Class[] interfaces =
new Class[] {interfaceClass, EventClientFactory.class};
final Class<?>[] interfaces =
new Class<?>[] {interfaceClass, EventClientFactory.class};
Object proxy =
Proxy.newProxyInstance(interfaceClass.getClassLoader(),
......@@ -156,7 +156,7 @@ public class EventClientConnection implements InvocationHandler,
// add/remove notification listener are routed to the EventClient
if (methodName.equals("addNotificationListener")
|| methodName.equals("removeNotificationListener")) {
final Class[] sig = method.getParameterTypes();
final Class<?>[] sig = method.getParameterTypes();
if (sig.length>1 &&
NotificationListener.class.isAssignableFrom(sig[1])) {
return invokeBroadcasterMethod(proxy,method,args);
......@@ -164,7 +164,7 @@ public class EventClientConnection implements InvocationHandler,
}
// subscribe/unsubscribe are also routed to the EventClient.
final Class clazz = method.getDeclaringClass();
final Class<?> clazz = method.getDeclaringClass();
if (clazz.equals(EventClientFactory.class)) {
return invokeEventClientSubscriberMethod(proxy,method,args);
}
......@@ -319,7 +319,7 @@ public class EventClientConnection implements InvocationHandler,
return true;
if (methodName.equals("equals")
&& Arrays.equals(method.getParameterTypes(),
new Class[] {Object.class})
new Class<?>[] {Object.class})
&& isLocal(proxy, method))
return true;
return false;
......@@ -430,13 +430,11 @@ public class EventClientConnection implements InvocationHandler,
* The {@code EventClient} is created lazily, when it is needed
* for the first time. If null, a default factory will be used
* (see {@link #createEventClient}).
* @return the
* @return the MBeanServerConnection.
**/
public static MBeanServerConnection getEventConnectionFor(
MBeanServerConnection connection,
Callable<EventClient> eventClientFactory) {
// if c already uses an EventClient no need to create a new one.
//
if (connection instanceof EventClientFactory
&& eventClientFactory != null)
throw new IllegalArgumentException("connection already uses EventClient");
......
......@@ -32,7 +32,7 @@ public class OrderClassLoaders extends ClassLoader {
this.cl2 = cl2;
}
protected Class findClass(String name) throws ClassNotFoundException {
protected Class<?> findClass(String name) throws ClassNotFoundException {
try {
return super.findClass(name);
} catch (ClassNotFoundException cne) {
......
......@@ -70,10 +70,13 @@ public class IdResolver {
*/
public static void registerElementById(Element element, String idValue) {
Document doc = element.getOwnerDocument();
WeakHashMap elementMap = (WeakHashMap) docMap.get(doc);
if(elementMap == null) {
elementMap = new WeakHashMap();
docMap.put(doc, elementMap);
WeakHashMap elementMap;
synchronized (docMap) {
elementMap = (WeakHashMap) docMap.get(doc);
if (elementMap == null) {
elementMap = new WeakHashMap();
docMap.put(doc, elementMap);
}
}
elementMap.put(idValue, new WeakReference(element));
}
......@@ -153,7 +156,10 @@ public class IdResolver {
private static Element getElementByIdType(Document doc, String id) {
if (log.isLoggable(java.util.logging.Level.FINE))
log.log(java.util.logging.Level.FINE, "getElementByIdType() Search for ID " + id);
WeakHashMap elementMap = (WeakHashMap) docMap.get(doc);
WeakHashMap elementMap;
synchronized (docMap) {
elementMap = (WeakHashMap) docMap.get(doc);
}
if (elementMap != null) {
WeakReference weakReference = (WeakReference) elementMap.get(id);
if (weakReference != null) {
......
......@@ -113,7 +113,7 @@ public class CertPathValidatorException extends GeneralSecurityException {
* permitted, and indicates that the cause is nonexistent or unknown.)
*/
public CertPathValidatorException(Throwable cause) {
this(null, cause);
this((cause == null ? null : cause.toString()), cause);
}
/**
......
/*
* Copyright 1999-2005 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1999-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
......@@ -27,17 +27,23 @@ package javax.management;
import java.util.ArrayList;
import java.util.Collection;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
/**
* Represents a list of values for attributes of an MBean. The methods
* used for the insertion of {@link javax.management.Attribute
* Attribute} objects in the <CODE>AttributeList</CODE> overrides the
* corresponding methods in the superclass
* <CODE>ArrayList</CODE>. This is needed in order to insure that the
* objects contained in the <CODE>AttributeList</CODE> are only
* <CODE>Attribute</CODE> objects. This avoids getting an exception
* when retrieving elements from the <CODE>AttributeList</CODE>.
* <p>Represents a list of values for attributes of an MBean. See the
* {@link MBeanServerConnection#getAttributes getAttributes} and
* {@link MBeanServerConnection#setAttributes setAttributes} methods of
* {@link MBeanServer} and {@link MBeanServerConnection}.</p>
*
* <p id="type-safe">For compatibility reasons, it is possible, though
* highly discouraged, to add objects to an {@code AttributeList} that are
* not instances of {@code Attribute}. However, an {@code AttributeList}
* can be made <em>type-safe</em>, which means that an attempt to add
* an object that is not an {@code Attribute} will produce an {@code
* IllegalArgumentException}. An {@code AttributeList} becomes type-safe
* when the method {@link #asList()} is called on it.</p>
*
* @since 1.5
*/
......@@ -58,8 +64,8 @@ import java.util.List;
*/
public class AttributeList extends ArrayList<Object> {
private transient boolean typeSafe;
private transient boolean tainted;
private transient volatile boolean typeSafe;
private transient volatile boolean tainted;
/* Serial version */
private static final long serialVersionUID = -4077085769279709076L;
......@@ -124,13 +130,63 @@ public class AttributeList extends ArrayList<Object> {
// Check for non-Attribute objects
//
checkTypeSafe(list);
adding(list);
// Build the List<Attribute>
//
super.addAll(list);
}
/**
* <p>Constructs an {@code AttributeList} containing the elements of
* the {@code Map} specified, in the order in which they appear in the
* {@code Map}'s {@link Map#entrySet entrySet}. For each <em>{@code
* key}</em> and <em>{@code value}</em> in the {@code Map}, the constructed
* {@code AttributeList} will contain {@link Attribute#Attribute
* Attribute(<em>key</em>, <em>value</em>)}.</p>
*
* @param map the {@code Map} defining the elements of the new
* {@code AttributeList}.
*/
public AttributeList(Map<String, ?> map) {
for (Map.Entry<String, ?> entry : map.entrySet())
add(new Attribute(entry.getKey(), entry.getValue()));
typeSafe = true;
}
/**
* <p>Return a {@code Map} that is a snapshot of the values in this
* {@code AttributeList}. Each key in the {@code Map} is the {@linkplain
* Attribute#getName() name} of an {@code Attribute} in the list, and each
* value is the corresponding {@linkplain Attribute#getValue() value} of
* that {@code Attribute}. The {@code AttributeList} and the {@code Map}
* are unrelated after the call, that is, changes to one do not affect the
* other.</p>
*
* <p>If the {@code AttributeList} contains more than one {@code Attribute}
* with the same name, then the {@code Map} will contain an entry
* for that name where the value is that of the last of those {@code
* Attribute}s.</p>
*
* @return the new {@code Map}.
*
* @throws IllegalArgumentException if this {@code AttributeList} contains
* an element that is not an {@code Attribute}.
*/
public Map<String, Object> toMap() {
Map<String, Object> map = new LinkedHashMap<String, Object>();
// We can't call adding(this) because we're not necessarily typeSafe
if (tainted)
throw new IllegalArgumentException("AttributeList contains non-Attribute");
for (Object x : this) {
Attribute a = (Attribute) x;
map.put(a.getName(), a.getValue());
}
return map;
}
/**
* Return a view of this list as a {@code List<Attribute>}.
* Changes to the returned value are reflected by changes
......@@ -154,12 +210,10 @@ public class AttributeList extends ArrayList<Object> {
*/
@SuppressWarnings("unchecked")
public List<Attribute> asList() {
if (!typeSafe) {
if (tainted)
checkTypeSafe(this);
typeSafe = true;
}
return (List<Attribute>) (List) this;
typeSafe = true;
if (tainted)
adding((Collection<?>) this); // will throw IllegalArgumentException
return (List<Attribute>) (List<?>) this;
}
/**
......@@ -175,7 +229,7 @@ public class AttributeList extends ArrayList<Object> {
* Inserts the attribute specified as an element at the position specified.
* Elements with an index greater than or equal to the current position are
* shifted up. If the index is out of range (index < 0 || index >
* size() a RuntimeOperationsException should be raised, wrapping the
* size()) a RuntimeOperationsException should be raised, wrapping the
* java.lang.IndexOutOfBoundsException thrown.
*
* @param object The <CODE>Attribute</CODE> object to be inserted.
......@@ -245,8 +299,7 @@ public class AttributeList extends ArrayList<Object> {
public boolean addAll(int index, AttributeList list) {
try {
return super.addAll(index, list);
}
catch (IndexOutOfBoundsException e) {
} catch (IndexOutOfBoundsException e) {
throw new RuntimeOperationsException(e,
"The specified index is out of range");
}
......@@ -258,96 +311,77 @@ public class AttributeList extends ArrayList<Object> {
* been called on this instance.
*/
/**
* {@inheritDoc}
* @throws IllegalArgumentException if this {@code AttributeList} is
* <a href="#type-safe">type-safe</a> and {@code element} is not an
* {@code Attribute}.
*/
@Override
public boolean add(Object o) {
if (!tainted)
tainted = isTainted(o);
if (typeSafe)
checkTypeSafe(o);
return super.add(o);
public boolean add(Object element) {
adding(element);
return super.add(element);
}
/**
* {@inheritDoc}
* @throws IllegalArgumentException if this {@code AttributeList} is
* <a href="#type-safe">type-safe</a> and {@code element} is not an
* {@code Attribute}.
*/
@Override
public void add(int index, Object element) {
if (!tainted)
tainted = isTainted(element);
if (typeSafe)
checkTypeSafe(element);
adding(element);
super.add(index, element);
}
/**
* {@inheritDoc}
* @throws IllegalArgumentException if this {@code AttributeList} is
* <a href="#type-safe">type-safe</a> and {@code c} contains an
* element that is not an {@code Attribute}.
*/
@Override
public boolean addAll(Collection<?> c) {
if (!tainted)
tainted = isTainted(c);
if (typeSafe)
checkTypeSafe(c);
adding(c);
return super.addAll(c);
}
/**
* {@inheritDoc}
* @throws IllegalArgumentException if this {@code AttributeList} is
* <a href="#type-safe">type-safe</a> and {@code c} contains an
* element that is not an {@code Attribute}.
*/
@Override
public boolean addAll(int index, Collection<?> c) {
if (!tainted)
tainted = isTainted(c);
if (typeSafe)
checkTypeSafe(c);
adding(c);
return super.addAll(index, c);
}
/**
* {@inheritDoc}
* @throws IllegalArgumentException if this {@code AttributeList} is
* <a href="#type-safe">type-safe</a> and {@code element} is not an
* {@code Attribute}.
*/
@Override
public Object set(int index, Object element) {
if (!tainted)
tainted = isTainted(element);
if (typeSafe)
checkTypeSafe(element);
adding(element);
return super.set(index, element);
}
/**
* IllegalArgumentException if o is a non-Attribute object.
*/
private static void checkTypeSafe(Object o) {
try {
o = (Attribute) o;
} catch (ClassCastException e) {
throw new IllegalArgumentException(e);
}
}
/**
* IllegalArgumentException if c contains any non-Attribute objects.
*/
private static void checkTypeSafe(Collection<?> c) {
try {
Attribute a;
for (Object o : c)
a = (Attribute) o;
} catch (ClassCastException e) {
throw new IllegalArgumentException(e);
}
}
/**
* Returns true if o is a non-Attribute object.
*/
private static boolean isTainted(Object o) {
try {
checkTypeSafe(o);
} catch (IllegalArgumentException e) {
return true;
}
return false;
private void adding(Object x) {
if (x == null || x instanceof Attribute)
return;
if (typeSafe)
throw new IllegalArgumentException("Not an Attribute: " + x);
else
tainted = true;
}
/**
* Returns true if c contains any non-Attribute objects.
*/
private static boolean isTainted(Collection<?> c) {
try {
checkTypeSafe(c);
} catch (IllegalArgumentException e) {
return true;
}
return false;
private void adding(Collection<?> c) {
for (Object x : c)
adding(x);
}
}
此差异已折叠。
......@@ -62,7 +62,7 @@ public class DefaultLoaderRepository {
*
* @exception ClassNotFoundException The specified class could not be found.
*/
public static Class loadClass(String className)
public static Class<?> loadClass(String className)
throws ClassNotFoundException {
return javax.management.loading.DefaultLoaderRepository.loadClass(className);
}
......@@ -82,7 +82,7 @@ public class DefaultLoaderRepository {
*
* @exception ClassNotFoundException The specified class could not be found.
*/
public static Class loadClassWithout(ClassLoader loader,String className)
public static Class<?> loadClassWithout(ClassLoader loader,String className)
throws ClassNotFoundException {
return javax.management.loading.DefaultLoaderRepository.loadClassWithout(loader, className);
}
......
......@@ -35,8 +35,8 @@ import java.io.Serializable;
// Javadoc imports:
import java.lang.management.MemoryUsage;
import java.util.Arrays;
import java.util.Locale;
import java.util.ResourceBundle;
import javax.management.openmbean.CompositeData;
import javax.management.openmbean.MXBeanMappingFactory;
import javax.management.openmbean.OpenMBeanAttributeInfoSupport;
......@@ -101,7 +101,7 @@ import javax.management.openmbean.OpenType;
*
* <tr><th>Name</th><th>Type</th><th>Used in</th><th>Meaning</th></tr>
*
* <tr><td><a name="defaultValue"><i>defaultValue</i></a><td>Object</td>
* <tr id="defaultValue"><td><i>defaultValue</i><td>Object</td>
* <td>MBeanAttributeInfo<br>MBeanParameterInfo</td>
*
* <td>Default value for an attribute or parameter. See
......@@ -118,19 +118,22 @@ import javax.management.openmbean.OpenType;
* deprecation, for example {@code "1.3 Replaced by the Capacity
* attribute"}.</td>
*
* <tr id="descriptionResourceBundleBaseName">
* <td>descriptionResource<br>BundleBaseName</td><td>String</td><td>Any</td>
* <tr><td id="descriptionResourceBundleBaseName"><i>descriptionResource<br>
* BundleBaseName</i></td><td>String</td><td>Any</td>
*
* <td>The base name for the {@link ResourceBundle} in which the key given in
* the {@code descriptionResourceKey} field can be found, for example
* {@code "com.example.myapp.MBeanResources"}.</td>
* {@code "com.example.myapp.MBeanResources"}. See
* {@link MBeanInfo#localizeDescriptions MBeanInfo.localizeDescriptions}.</td>
*
* <tr id="descriptionResourceKey">
* <td>descriptionResourceKey</td><td>String</td><td>Any</td>
* <tr><td id="descriptionResourceKey"><i>descriptionResourceKey</i></td>
* <td>String</td><td>Any</td>
*
* <td>A resource key for the description of this element. In
* conjunction with the {@code descriptionResourceBundleBaseName},
* this can be used to find a localized version of the description.</td>
* this can be used to find a localized version of the description.
* See {@link MBeanInfo#localizeDescriptions MBeanInfo.localizeDescriptions}.
* </td>
*
* <tr><td>enabled</td><td>String</td>
* <td>MBeanAttributeInfo<br>MBeanNotificationInfo<br>MBeanOperationInfo</td>
......@@ -144,7 +147,7 @@ import javax.management.openmbean.OpenType;
* might be disabled if it cannot currently be emitted but could be in
* other circumstances.</td>
*
* <tr><td><a name="immutableInfo"><i>immutableInfo</i></a><td>String</td>
* <tr id="immutableInfo"><td><i>immutableInfo</i><td>String</td>
* <td>MBeanInfo</td>
*
* <td>The string {@code "true"} or {@code "false"} according as this
......@@ -153,9 +156,11 @@ import javax.management.openmbean.OpenType;
* the lifetime of the MBean. Hence, a client can read it once and
* cache the read value. When this field is false or absent, there is
* no such guarantee, although that does not mean that the MBeanInfo
* will necessarily change.</td>
* will necessarily change. See also the <a
* href="MBeanInfo.html#info-changed">{@code "jmx.mbean.info.changed"}</a>
* notification.</td>
*
* <tr><td>infoTimeout</td><td>String<br>Long</td><td>MBeanInfo</td>
* <tr id="infoTimeout"><td>infoTimeout</td><td>String<br>Long</td><td>MBeanInfo</td>
*
* <td>The time in milli-seconds that the MBeanInfo can reasonably be
* expected to be unchanged. The value can be a {@code Long} or a
......@@ -164,9 +169,11 @@ import javax.management.openmbean.OpenType;
* that the MBeanInfo is not likely to change within this period and
* therefore can be cached. When this field is missing or has the
* value zero, it is not recommended to cache the MBeanInfo unless it
* has the {@code immutableInfo} set to {@code true}.</td></tr>
* has the {@code immutableInfo} set to {@code true} or it has <a
* href="MBeanInfo.html#info-changed">{@code "jmx.mbean.info.changed"}</a> in
* its {@link MBeanNotificationInfo} array.</td></tr>
*
* <tr><td><a name="interfaceClassName"><i>interfaceClassName</i></a></td>
* <tr id="interfaceClassName"><td><i>interfaceClassName</i></td>
* <td>String</td><td>MBeanInfo</td>
*
* <td>The Java interface name for a Standard MBean or MXBean, as
......@@ -175,19 +182,26 @@ import javax.management.openmbean.OpenType;
* StandardMBean} class will have this field in its MBeanInfo
* Descriptor.</td>
*
* <tr><td><a name="legalValues"><i>legalValues</i></a></td>
* <tr id="legalValues"><td><i>legalValues</i></td>
* <td>{@literal Set<?>}</td><td>MBeanAttributeInfo<br>MBeanParameterInfo</td>
*
* <td>Legal values for an attribute or parameter. See
* {@link javax.management.openmbean}.</td>
*
* <tr><td><a name="maxValue"><i>maxValue</i></a><td>Object</td>
* <tr id="locale"><td><i>locale</i></td>
* <td>String</td><td>Any</td>
*
* <td>The {@linkplain Locale locale} of the description in this
* {@code MBeanInfo}, {@code MBeanAttributeInfo}, etc, as returned
* by {@link Locale#toString()}.</td>
*
* <tr id="maxValue"><td><i>maxValue</i><td>Object</td>
* <td>MBeanAttributeInfo<br>MBeanParameterInfo</td>
*
* <td>Maximum legal value for an attribute or parameter. See
* {@link javax.management.openmbean}.</td>
*
* <tr><td><a name="metricType">metricType</a><td>String</td>
* <tr id="metricType"><td>metricType</td><td>String</td>
* <td>MBeanAttributeInfo<br>MBeanOperationInfo</td>
*
* <td>The type of a metric, one of the strings "counter" or "gauge".
......@@ -200,13 +214,13 @@ import javax.management.openmbean.OpenType;
* that can increase or decrease. Examples might be the number of
* open connections or a cache hit rate or a temperature reading.
*
* <tr><td><a name="minValue"><i>minValue</i></a><td>Object</td>
* <tr id="minValue"><td><i>minValue</i><td>Object</td>
* <td>MBeanAttributeInfo<br>MBeanParameterInfo</td>
*
* <td>Minimum legal value for an attribute or parameter. See
* {@link javax.management.openmbean}.</td>
*
* <tr><td><a name="mxbean"><i>mxbean</i></a><td>String</td>
* <tr id="mxbean"><td><i>mxbean</i><td>String</td>
* <td>MBeanInfo</td>
*
* <td>The string {@code "true"} or {@code "false"} according as this
......@@ -223,7 +237,7 @@ import javax.management.openmbean.OpenType;
* MXBean, if it was not the {@linkplain MXBeanMappingFactory#DEFAULT default}
* one.</td>
*
* <tr><td><a name="openType"><i>openType</i></a><td>{@link OpenType}</td>
* <tr id="openType"><td><i>openType</i><td>{@link OpenType}</td>
* <td>MBeanAttributeInfo<br>MBeanOperationInfo<br>MBeanParameterInfo</td>
*
* <td><p>The Open Type of this element. In the case of {@code
......@@ -240,7 +254,7 @@ import javax.management.openmbean.OpenType;
* which case it indicates the Open Type that the {@link
* Notification#getUserData() user data} will have.</td>
*
* <tr><td><a name="originalType"><i>originalType</i></a><td>String</td>
* <tr id="originalType"><td><i>originalType</i><td>String</td>
* <td>MBeanAttributeInfo<br>MBeanOperationInfo<br>MBeanParameterInfo</td>
*
* <td><p>The original Java type of this element as it appeared in the
......@@ -282,11 +296,132 @@ import javax.management.openmbean.OpenType;
*
* </table>
*
* <p>Some additional fields are defined by Model MBeans. See
* {@link javax.management.modelmbean.ModelMBeanInfo ModelMBeanInfo}
* and related classes and the chapter "Model MBeans" of the
* <a href="http://java.sun.com/products/JavaManagement/download.html">
* JMX Specification</a>.</p>
* <p>Some additional fields are defined by Model MBeans. See the
* information for <a href="modelmbean/ModelMBeanInfo.html#descriptor"><!--
* -->{@code ModelMBeanInfo}</a>,
* <a href="modelmbean/ModelMBeanAttributeInfo.html#descriptor"><!--
* -->{@code ModelMBeanAttributeInfo}</a>,
* <a href="modelmbean/ModelMBeanConstructorInfo.html#descriptor"><!--
* -->{@code ModelMBeanConstructorInfo}</a>,
* <a href="modelmbean/ModelMBeanNotificationInfo.html#descriptor"><!--
* -->{@code ModelMBeanNotificationInfo}</a>, and
* <a href="modelmbean/ModelMBeanOperationInfo.html#descriptor"><!--
* -->{@code ModelMBeanOperationInfo}</a>, as
* well as the chapter "Model MBeans" of the <a
* href="http://java.sun.com/products/JavaManagement/download.html">JMX
* Specification</a>. The following table summarizes these fields. Note
* that when the Type in this table is Number, a String that is the decimal
* representation of a Long can also be used.</p>
*
* <p>Nothing prevents the use of these fields in MBeans that are not Model
* MBeans. The <a href="#displayName">displayName</a>, <a href="#severity"><!--
* -->severity</a>, and <a href="#visibility">visibility</a> fields are of
* interest outside Model MBeans, for example. But only Model MBeans have
* a predefined behavior for these fields.</p>
*
* <table border="1" cellpadding="5">
*
* <tr><th>Name</th><th>Type</th><th>Used in</th><th>Meaning</th></tr>
*
* <tr><td>class</td><td>String</td><td>ModelMBeanOperationInfo</td>
* <td>Class where method is defined (fully qualified).</td></tr>
*
* <tr><td>currencyTimeLimit</td><td>Number</td>
* <td>ModelMBeanInfo<br>ModelMBeanAttributeInfo<br>ModelMBeanOperationInfo</td>
* <td>How long cached value is valid: &lt;0 never, =0 always,
* &gt;0 seconds.</td></tr>
*
* <tr><td>default</td><td>Object</td><td>ModelMBeanAttributeInfo</td>
* <td>Default value for attribute.</td></tr>
*
* <tr><td>descriptorType</td><td>String</td><td>Any</td>
* <td>Type of descriptor, "mbean", "attribute", "constructor", "operation",
* or "notification".</td></tr>
*
* <tr id="displayName"><td>displayName</td><td>String</td><td>Any</td>
* <td>Human readable name of this item.</td></tr>
*
* <tr><td>export</td><td>String</td><td>ModelMBeanInfo</td>
* <td>Name to be used to export/expose this MBean so that it is
* findable by other JMX Agents.</td></tr>
*
* <tr><td>getMethod</td><td>String</td><td>ModelMBeanAttributeInfo</td>
* <td>Name of operation descriptor for get method.</td></tr>
*
* <tr><td>lastUpdatedTimeStamp</td><td>Number</td>
* <td>ModelMBeanAttributeInfo<br>ModelMBeanOperationInfo</td>
* <td>When <a href="#value-field">value</a> was set.</td></tr>
*
* <tr><td>log</td><td>String</td><td>ModelMBeanInfo<br>ModelMBeanNotificationInfo</td>
* <td>t or T: log all notifications, f or F: log no notifications.</td></tr>
*
* <tr><td>logFile</td><td>String</td><td>ModelMBeanInfo<br>ModelMBeanNotificationInfo</td>
* <td>Fully qualified filename to log events to.</td></tr>
*
* <tr><td>messageID</td><td>String</td><td>ModelMBeanNotificationInfo</td>
* <td>Unique key for message text (to allow translation, analysis).</td></tr>
*
* <tr><td>messageText</td><td>String</td><td>ModelMBeanNotificationInfo</td>
* <td>Text of notification.</td></tr>
*
* <tr><td>name</td><td>String</td><td>Any</td>
* <td>Name of this item.</td></tr>
*
* <tr><td>persistFile</td><td>String</td><td>ModelMBeanInfo</td>
* <td>File name into which the MBean should be persisted.</td></tr>
*
* <tr><td>persistLocation</td><td>String</td><td>ModelMBeanInfo</td>
* <td>The fully qualified directory name where the MBean should be
* persisted (if appropriate).</td></tr>
*
* <tr><td>persistPeriod</td><td>Number</td>
* <td>ModelMBeanInfo<br>ModelMBeanAttributeInfo</td>
* <td>Frequency of persist cycle in seconds. Used when persistPolicy is
* "OnTimer" or "NoMoreOftenThan".</td></tr>
*
* <tr><td>persistPolicy</td><td>String</td>
* <td>ModelMBeanInfo<br>ModelMBeanAttributeInfo</td>
* <td>One of: OnUpdate|OnTimer|NoMoreOftenThan|OnUnregister|Always|Never.
* See the section "MBean Descriptor Fields" in the JMX specification
* document.</td></tr>
*
* <tr><td>presentationString</td><td>String</td><td>Any</td>
* <td>XML formatted string to allow presentation of data.</td></tr>
*
* <tr><td>protocolMap</td><td>Descriptor</td><td>ModelMBeanAttributeInfo</td>
* <td>See the section "Protocol Map Support" in the JMX specification
* document. Mappings must be appropriate for the attribute and entries
* can be updated or augmented at runtime.</td></tr>
*
* <tr><td>role</td><td>String</td>
* <td>ModelMBeanConstructorInfo<br>ModelMBeanOperationInfo</td>
* <td>One of "constructor", "operation", "getter", or "setter".</td></tr>
*
* <tr><td>setMethod</td><td>String</td><td>ModelMBeanAttributeInfo</td>
* <td>Name of operation descriptor for set method.</td></tr>
*
* <tr id="severity"><td>severity</td><td>Number</td>
* <td>ModelMBeanNotificationInfo</td>
* <td>0-6 where 0: unknown; 1: non-recoverable;
* 2: critical, failure; 3: major, severe;
* 4: minor, marginal, error; 5: warning;
* 6: normal, cleared, informative</td></tr>
*
* <tr><td>targetObject</td><td>Object</td><td>ModelMBeanOperationInfo</td>
* <td>Object on which to execute this method.</td></tr>
*
* <tr><td>targetType</td><td>String</td><td>ModelMBeanOperationInfo</td>
* <td>type of object reference for targetObject. Can be:
* ObjectReference | Handle | EJBHandle | IOR | RMIReference.</td></tr>
*
* <tr id="value-field"><td>value</td><td>Object</td>
* <td>ModelMBeanAttributeInfo<br>ModelMBeanOperationInfo</td>
* <td>Current (cached) value for attribute or operation.</td></tr>
*
* <tr id="visibility"><td>visibility</td><td>Number</td><td>Any</td>
* <td>1-4 where 1: always visible, 4: rarely visible.</td></tr>
*
* </table>
*
* @since 1.5
*/
......@@ -439,7 +574,7 @@ public interface Descriptor extends Serializable, Cloneable
public boolean isValid() throws RuntimeOperationsException;
/**
* Compares this descriptor to the given object. The objects are equal if
* <p>Compares this descriptor to the given object. The objects are equal if
* the given object is also a Descriptor, and if the two Descriptors have
* the same field names (possibly differing in case) and the same
* associated values. The respective values for a field in the two
......
......@@ -70,7 +70,7 @@ public class JMRuntimeException extends RuntimeException {
try {
java.lang.reflect.Method initCause =
Throwable.class.getMethod("initCause",
new Class[] {Throwable.class});
new Class<?>[] {Throwable.class});
initCause.invoke(this, new Object[] {cause});
} catch (Exception e) {
// OK: just means we won't have debugging info
......
......@@ -30,6 +30,7 @@ import com.sun.jmx.mbeanserver.MBeanInjector;
import com.sun.jmx.remote.util.ClassLogger;
import java.beans.BeanInfo;
import java.beans.PropertyDescriptor;
import java.io.IOException;
import java.io.Serializable;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
......@@ -37,6 +38,7 @@ import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Map;
import java.util.TreeMap;
import javax.management.namespace.JMXNamespaces;
import javax.management.openmbean.MXBeanMappingFactory;
/**
......@@ -60,6 +62,21 @@ public class JMX {
*/
public static final String DEFAULT_VALUE_FIELD = "defaultValue";
/**
* The name of the <a
* href="Descriptor.html#descriptionResourceBundleBaseName">{@code
* descriptionResourceBundleBaseName}</a> field.
*/
public static final String DESCRIPTION_RESOURCE_BUNDLE_BASE_NAME_FIELD =
"descriptionResourceBundleBaseName";
/**
* The name of the <a href="Descriptor.html#descriptionResourceKey">{@code
* descriptionResourceKey}</a> field.
*/
public static final String DESCRIPTION_RESOURCE_KEY_FIELD =
"descriptionResourceKey";
/**
* The name of the <a href="Descriptor.html#immutableInfo">{@code
* immutableInfo}</a> field.
......@@ -78,6 +95,12 @@ public class JMX {
*/
public static final String LEGAL_VALUES_FIELD = "legalValues";
/**
* The name of the <a href="Descriptor.html#locale">{@code locale}</a>
* field.
*/
public static final String LOCALE_FIELD = "locale";
/**
* The name of the <a href="Descriptor.html#maxValue">{@code
* maxValue}</a> field.
......@@ -120,13 +143,12 @@ public class JMX {
* <p>Options to apply to an MBean proxy or to an instance of {@link
* StandardMBean}.</p>
*
* <p>For example, to specify a custom {@link MXBeanMappingFactory}
* for a {@code StandardMBean}, you might write this:</p>
* <p>For example, to specify the "wrapped object visible" option for a
* {@code StandardMBean}, you might write this:</p>
*
* <pre>
* MXBeanMappingFactory factory = new MyMXBeanMappingFactory();
* JMX.MBeanOptions opts = new JMX.MBeanOptions();
* opts.setMXBeanMappingFactory(factory);
* StandardMBean.Options opts = new StandardMBean.Options();
* opts.setWrappedObjectVisible(true);
* StandardMBean mbean = new StandardMBean(impl, intf, opts);
* </pre>
*
......@@ -463,6 +485,12 @@ public class JMX {
* likewise for the other methods of {@link
* NotificationBroadcaster} and {@link NotificationEmitter}.</p>
*
* <p>This method is equivalent to {@link
* #newMBeanProxy(MBeanServerConnection, ObjectName, Class, JMX.MBeanOptions)
* newMBeanProxy(connection, objectName, interfaceClass, opts)}, where
* {@code opts} is a {@link JMX.ProxyOptions} representing the
* {@code notificationEmitter} parameter.</p>
*
* @param connection the MBean server to forward to.
* @param objectName the name of the MBean within
* {@code connection} to forward to.
......@@ -555,10 +583,6 @@ public class JMX {
*
* </ul>
*
* <p>The object returned by this method is a
* {@link Proxy} whose {@code InvocationHandler} is an
* {@link MBeanServerInvocationHandler}.</p>
*
* <p>This method is equivalent to {@link
* #newMXBeanProxy(MBeanServerConnection, ObjectName, Class,
* boolean) newMXBeanProxy(connection, objectName, interfaceClass,
......@@ -601,6 +625,17 @@ public class JMX {
* likewise for the other methods of {@link
* NotificationBroadcaster} and {@link NotificationEmitter}.</p>
*
* <p>This method is equivalent to {@link
* #newMBeanProxy(MBeanServerConnection, ObjectName, Class, JMX.MBeanOptions)
* newMBeanProxy(connection, objectName, interfaceClass, opts)}, where
* {@code opts} is a {@link JMX.ProxyOptions} where the {@link
* JMX.ProxyOptions#getMXBeanMappingFactory() MXBeanMappingFactory}
* property is
* {@link MXBeanMappingFactory#forInterface(Class)
* MXBeanMappingFactory.forInterface(interfaceClass)} and the {@link
* JMX.ProxyOptions#isNotificationEmitter() notificationEmitter} property
* is equal to the {@code notificationEmitter} parameter.</p>
*
* @param connection the MBean server to forward to.
* @param objectName the name of the MBean within
* {@code connection} to forward to.
......@@ -655,6 +690,36 @@ public class JMX {
* arbitrary Java types and Open Types.</li>
* </ul>
*
* <p>The object returned by this method is a
* {@link Proxy} whose {@code InvocationHandler} is an
* {@link MBeanServerInvocationHandler}. This means that it is possible
* to retrieve the parameters that were used to produce the proxy. If the
* proxy was produced as follows...</p>
*
* <pre>
* FooMBean proxy =
* JMX.newMBeanProxy(connection, objectName, FooMBean.class, opts);
* </pre>
*
* <p>...then you can get the {@code MBeanServerInvocationHandler} like
* this...</p>
*
* <pre>
* MBeanServerInvocationHandler mbsih = (MBeanServerInvocationHandler)
* {@link Proxy#getInvocationHandler(Object)
* Proxy.getInvocationHandler}(proxy);
* </pre>
*
* <p>...and you can retrieve {@code connection}, {@code
* objectName}, and {@code opts} using the {@link
* MBeanServerInvocationHandler#getMBeanServerConnection()
* getMBeanServerConnection()}, {@link
* MBeanServerInvocationHandler#getObjectName() getObjectName()}, and
* {@link MBeanServerInvocationHandler#getMBeanOptions() getMBeanOptions()}
* methods on {@code mbsih}. You can retrieve {@code FooMBean.class}
* using {@code proxy.getClass().}{@link
* Class#getInterfaces() getInterfaces()}.</p>
*
* @param connection the MBean server to forward to.
* @param objectName the name of the MBean within
* {@code connection} to forward to.
......@@ -703,12 +768,12 @@ public class JMX {
InvocationHandler handler = new MBeanServerInvocationHandler(
connection, objectName, opts);
final Class[] interfaces;
final Class<?>[] interfaces;
if (notificationEmitter) {
interfaces =
new Class<?>[] {interfaceClass, NotificationEmitter.class};
} else
interfaces = new Class[] {interfaceClass};
interfaces = new Class<?>[] {interfaceClass};
Object proxy = Proxy.newProxyInstance(
interfaceClass.getClassLoader(),
interfaces,
......@@ -765,4 +830,80 @@ public class JMX {
((DynamicWrapperMBean) mbean).getWrappedObject() : mbean;
return (MBeanInjector.injectsSendNotification(resource));
}
/**
* <p>Return the version of the JMX specification that a (possibly remote)
* MBean Server is using. The JMX specification described in this
* documentation is version 2.0. The earlier versions that might be
* reported by this method are 1.0, 1.1, 1.2, and 1.4. (There is no 1.3.)
* All of these versions and all future versions can be compared using
* {@link String#compareTo(String)}. So, for example, to tell if
* {@code mbsc} is running at least version 2.0 you can write:</p>
*
* <pre>
* String version = JMX.getSpecificationVersion(mbsc, null);
* boolean atLeast2dot0 = (version.compareTo("2.0") >= 0);
* </pre>
*
* <p>A remote MBean Server might be running an earlier version of the
* JMX API, and in that case <a href="package-summary.html#interop">certain
* features</a> might not be available in it.</p>
*
* <p>The version of the MBean Server {@code mbsc} is not necessarily
* the version of all namespaces within that MBean Server, for example
* if some of them use {@link javax.management.namespace.JMXRemoteNamespace
* JMXRemoteNamespace}. To determine the version of the namespace
* that a particular MBean is in, give its name as the {@code mbeanName}
* parameter.</p>
*
* @param mbsc a connection to an MBean Server.
*
* @param mbeanName the name of an MBean within that MBean Server, or null.
* If non-null, the namespace of this name, as determined by
* {@link JMXNamespaces#getContainingNamespace
* JMXNamespaces.getContainingNamespace}, is the one whose specification
* version will be returned.
*
* @return the JMX specification version reported by that MBean Server.
*
* @throws IllegalArgumentException if {@code mbsc} is null, or if
* {@code mbeanName} includes a wildcard character ({@code *} or {@code ?})
* in its namespace.
*
* @throws IOException if the version cannot be obtained, either because
* there is a communication problem or because the remote MBean Server
* does not have the appropriate {@linkplain
* MBeanServerDelegateMBean#getSpecificationVersion() attribute}.
*
* @see <a href="package-summary.html#interop">Interoperability between
* versions of the JMX specification</a>
* @see MBeanServerDelegateMBean#getSpecificationVersion
*/
public static String getSpecificationVersion(
MBeanServerConnection mbsc, ObjectName mbeanName)
throws IOException {
if (mbsc == null)
throw new IllegalArgumentException("Null MBeanServerConnection");
String namespace;
if (mbeanName == null)
namespace = "";
else
namespace = JMXNamespaces.getContainingNamespace(mbeanName);
if (namespace.contains("*") || namespace.contains("?")) {
throw new IllegalArgumentException(
"ObjectName contains namespace wildcard: " + mbeanName);
}
try {
if (namespace.length() > 0)
mbsc = JMXNamespaces.narrowToNamespace(mbsc, namespace);
return (String) mbsc.getAttribute(
MBeanServerDelegate.DELEGATE_NAME, "SpecificationVersion");
} catch (IOException e) {
throw e;
} catch (Exception e) {
throw new IOException(e);
}
}
}
......@@ -316,7 +316,7 @@ public class MBeanAttributeInfo extends MBeanFeatureInfo implements Cloneable {
*/
private static String attributeType(Method getter, Method setter)
throws IntrospectionException {
Class type = null;
Class<?> type = null;
if (getter != null) {
if (getter.getParameterTypes().length != 0) {
......@@ -330,7 +330,7 @@ public class MBeanAttributeInfo extends MBeanFeatureInfo implements Cloneable {
}
if (setter != null) {
Class params[] = setter.getParameterTypes();
Class<?> params[] = setter.getParameterTypes();
if (params.length != 1) {
throw new IntrospectionException("bad setter arg count");
}
......
......@@ -64,7 +64,7 @@ public class MBeanConstructorInfo extends MBeanFeatureInfo implements Cloneable
* @param constructor The <CODE>java.lang.reflect.Constructor</CODE>
* object describing the MBean constructor.
*/
public MBeanConstructorInfo(String description, Constructor constructor) {
public MBeanConstructorInfo(String description, Constructor<?> constructor) {
this(constructor.getName(), description,
constructorSignature(constructor),
Introspector.descriptorForElement(constructor));
......@@ -210,8 +210,8 @@ public class MBeanConstructorInfo extends MBeanFeatureInfo implements Cloneable
return hash;
}
private static MBeanParameterInfo[] constructorSignature(Constructor cn) {
final Class[] classes = cn.getParameterTypes();
private static MBeanParameterInfo[] constructorSignature(Constructor<?> cn) {
final Class<?>[] classes = cn.getParameterTypes();
final Annotation[][] annots = cn.getParameterAnnotations();
return MBeanOperationInfo.parameters(classes, annots);
}
......
......@@ -308,17 +308,18 @@ public class MBeanOperationInfo extends MBeanFeatureInfo implements Cloneable {
wrong should be less than the penalty we would pay if it were
right and we needlessly hashed in the description and the
parameter array. */
@Override
public int hashCode() {
return getName().hashCode() ^ getReturnType().hashCode();
}
private static MBeanParameterInfo[] methodSignature(Method method) {
final Class[] classes = method.getParameterTypes();
final Class<?>[] classes = method.getParameterTypes();
final Annotation[][] annots = method.getParameterAnnotations();
return parameters(classes, annots);
}
static MBeanParameterInfo[] parameters(Class[] classes,
static MBeanParameterInfo[] parameters(Class<?>[] classes,
Annotation[][] annots) {
final MBeanParameterInfo[] params =
new MBeanParameterInfo[classes.length];
......
......@@ -377,19 +377,19 @@ public interface MBeanServer extends MBeanServerConnection {
* MBean will not be registered.
* @exception RuntimeMBeanException If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws a
* <CODE>RuntimeException</CODE>, the <CODE>registerMBean<CODE> method will
* <CODE>RuntimeException</CODE>, the <CODE>registerMBean</CODE> method will
* throw a <CODE>RuntimeMBeanException</CODE>, although the MBean
* registration succeeded. In such a case, the MBean will be actually
* registered even though the <CODE>registerMBean<CODE> method
* registered even though the <CODE>registerMBean</CODE> method
* threw an exception. Note that <CODE>RuntimeMBeanException</CODE> can
* also be thrown by <CODE>preRegister</CODE>, in which case the MBean
* will not be registered.
* @exception RuntimeErrorException If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws an
* <CODE>Error</CODE>, the <CODE>registerMBean<CODE> method will
* <CODE>Error</CODE>, the <CODE>registerMBean</CODE> method will
* throw a <CODE>RuntimeErrorException</CODE>, although the MBean
* registration succeeded. In such a case, the MBean will be actually
* registered even though the <CODE>registerMBean<CODE> method
* registered even though the <CODE>registerMBean</CODE> method
* threw an exception. Note that <CODE>RuntimeErrorException</CODE> can
* also be thrown by <CODE>preRegister</CODE>, in which case the MBean
* will not be registered.
......@@ -411,6 +411,8 @@ public interface MBeanServer extends MBeanServerConnection {
* is sent as described <a href="#notif">above</a>.</p>
*
* @throws RuntimeOperationsException {@inheritDoc}
* @throws RuntimeMBeanException {@inheritDoc}
* @throws RuntimeErrorException {@inheritDoc}
*/
public void unregisterMBean(ObjectName name)
throws InstanceNotFoundException, MBeanRegistrationException;
......
......@@ -76,7 +76,9 @@ public interface MBeanServerConnection extends NotificationManager {
* <CODE>preRegister</CODE> (<CODE>MBeanRegistration</CODE>
* interface) method of the MBean has thrown an exception. The
* MBean will not be registered.
* @exception RuntimeMBeanException If the <CODE>postRegister</CODE>
* @exception RuntimeMBeanException If the MBean's constructor or its
* {@code preRegister} or {@code postRegister} method threw
* a {@code RuntimeException}. If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws a
* <CODE>RuntimeException</CODE>, the <CODE>createMBean</CODE> method will
* throw a <CODE>RuntimeMBeanException</CODE>, although the MBean creation
......@@ -148,7 +150,9 @@ public interface MBeanServerConnection extends NotificationManager {
* <CODE>preRegister</CODE> (<CODE>MBeanRegistration</CODE>
* interface) method of the MBean has thrown an exception. The
* MBean will not be registered.
* @exception RuntimeMBeanException If the <CODE>postRegister</CODE>
* @exception RuntimeMBeanException If the MBean's constructor or its
* {@code preRegister} or {@code postRegister} method threw
* a {@code RuntimeException}. If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws a
* <CODE>RuntimeException</CODE>, the <CODE>createMBean</CODE> method will
* throw a <CODE>RuntimeMBeanException</CODE>, although the MBean creation
......@@ -223,7 +227,9 @@ public interface MBeanServerConnection extends NotificationManager {
* <CODE>preRegister</CODE> (<CODE>MBeanRegistration</CODE>
* interface) method of the MBean has thrown an exception. The
* MBean will not be registered.
* @exception RuntimeMBeanException If the <CODE>postRegister</CODE>
* @exception RuntimeMBeanException If the MBean's constructor or its
* {@code preRegister} or {@code postRegister} method threw
* a {@code RuntimeException}. If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws a
* <CODE>RuntimeException</CODE>, the <CODE>createMBean</CODE> method will
* throw a <CODE>RuntimeMBeanException</CODE>, although the MBean creation
......@@ -295,7 +301,9 @@ public interface MBeanServerConnection extends NotificationManager {
* <CODE>preRegister</CODE> (<CODE>MBeanRegistration</CODE>
* interface) method of the MBean has thrown an exception. The
* MBean will not be registered.
* @exception RuntimeMBeanException If the <CODE>postRegister</CODE>
* @exception RuntimeMBeanException The MBean's constructor or its
* {@code preRegister} or {@code postRegister} method threw
* a {@code RuntimeException}. If the <CODE>postRegister</CODE>
* (<CODE>MBeanRegistration</CODE> interface) method of the MBean throws a
* <CODE>RuntimeException</CODE>, the <CODE>createMBean</CODE> method will
* throw a <CODE>RuntimeMBeanException</CODE>, although the MBean creation
......@@ -524,8 +532,30 @@ public interface MBeanServerConnection extends NotificationManager {
/**
* Enables the values of several attributes of a named MBean. The MBean
* is identified by its object name.
* <p>Retrieves the values of several attributes of a named MBean. The MBean
* is identified by its object name.</p>
*
* <p>If one or more attributes cannot be retrieved for some reason, they
* will be omitted from the returned {@code AttributeList}. The caller
* should check that the list is the same size as the {@code attributes}
* array. To discover what problem prevented a given attribute from being
* retrieved, call {@link #getAttribute getAttribute} for that attribute.</p>
*
* <p>Here is an example of calling this method and checking that it
* succeeded in retrieving all the requested attributes:</p>
*
* <pre>
* String[] attrNames = ...;
* AttributeList list = mbeanServerConnection.getAttributes(objectName, attrNames);
* if (list.size() == attrNames.length)
* System.out.println("All attributes were retrieved successfully");
* else {
* {@code List<String>} missing = new {@code ArrayList<String>}(<!--
* -->{@link java.util.Arrays#asList Arrays.asList}(attrNames));
* missing.removeAll(list.toMap().keySet());
* System.out.println("Did not retrieve: " + missing);
* }
* </pre>
*
* @param name The object name of the MBean from which the
* attributes are retrieved.
......@@ -549,6 +579,7 @@ public interface MBeanServerConnection extends NotificationManager {
throws InstanceNotFoundException, ReflectionException,
IOException;
/**
* Sets the value of a specific attribute of a named MBean. The MBean
* is identified by its object name.
......@@ -584,10 +615,36 @@ public interface MBeanServerConnection extends NotificationManager {
ReflectionException, IOException;
/**
* Sets the values of several attributes of a named MBean. The MBean is
* identified by its object name.
* <p>Sets the values of several attributes of a named MBean. The MBean is
* identified by its object name.</p>
*
* <p>If one or more attributes cannot be set for some reason, they will be
* omitted from the returned {@code AttributeList}. The caller should check
* that the input {@code AttributeList} is the same size as the output one.
* To discover what problem prevented a given attribute from being retrieved,
* it will usually be possible to call {@link #setAttribute setAttribute}
* for that attribute, although this is not guaranteed to work. (For
* example, the values of two attributes may have been rejected because
* they were inconsistent with each other. Setting one of them alone might
* be allowed.)<p>
*
* <p>Here is an example of calling this method and checking that it
* succeeded in setting all the requested attributes:</p>
*
* <pre>
* AttributeList inputAttrs = ...;
* AttributeList outputAttrs = mbeanServerConnection.setAttributes(<!--
* -->objectName, inputAttrs);
* if (inputAttrs.size() == outputAttrs.size())
* System.out.println("All attributes were set successfully");
* else {
* {@code List<String>} missing = new {@code ArrayList<String>}(<!--
* -->inputAttrs.toMap().keySet());
* missing.removeAll(outputAttrs.toMap().keySet());
* System.out.println("Did not set: " + missing);
* }
* </pre>
*
* @param name The object name of the MBean within which the
* attributes are to be set.
......@@ -614,7 +671,39 @@ public interface MBeanServerConnection extends NotificationManager {
throws InstanceNotFoundException, ReflectionException, IOException;
/**
* Invokes an operation on an MBean.
* <p>Invokes an operation on an MBean.</p>
*
* <p>Because of the need for a {@code signature} to differentiate
* possibly-overloaded operations, it is much simpler to invoke operations
* through an {@linkplain JMX#newMBeanProxy(MBeanServerConnection, ObjectName,
* Class) MBean proxy} where possible. For example, suppose you have a
* Standard MBean interface like this:</p>
*
* <pre>
* public interface FooMBean {
* public int countMatches(String[] patterns, boolean ignoreCase);
* }
* </pre>
*
* <p>The {@code countMatches} operation can be invoked as follows:</p>
*
* <pre>
* String[] myPatterns = ...;
* int count = (Integer) mbeanServerConnection.invoke(
* objectName,
* "countMatches",
* new Object[] {myPatterns, true},
* new String[] {String[].class.getName(), boolean.class.getName()});
* </pre>
*
* <p>Alternatively, it can be invoked through a proxy as follows:</p>
*
* <pre>
* String[] myPatterns = ...;
* FooMBean fooProxy = JMX.newMBeanProxy(
* mbeanServerConnection, objectName, FooMBean.class);
* int count = fooProxy.countMatches(myPatterns, true);
* </pre>
*
* @param name The object name of the MBean on which the method is
* to be invoked.
......@@ -622,7 +711,8 @@ public interface MBeanServerConnection extends NotificationManager {
* @param params An array containing the parameters to be set when
* the operation is invoked
* @param signature An array containing the signature of the
* operation. The class objects will be loaded using the same
* operation, an array of class names in the format returned by
* {@link Class#getName()}. The class objects will be loaded using the same
* class loader as the one used for loading the MBean on which the
* operation was invoked.
*
......
......@@ -747,7 +747,7 @@ public class MBeanServerFactory {
* Load the builder class through the context class loader.
* @param builderClassName The name of the builder class.
**/
private static Class loadBuilderClass(String builderClassName)
private static Class<?> loadBuilderClass(String builderClassName)
throws ClassNotFoundException {
final ClassLoader loader =
Thread.currentThread().getContextClassLoader();
......@@ -767,7 +767,7 @@ public class MBeanServerFactory {
* If any checked exception needs to be thrown, it is embedded in
* a JMRuntimeException.
**/
private static MBeanServerBuilder newBuilder(Class builderClass) {
private static MBeanServerBuilder newBuilder(Class<?> builderClass) {
try {
final Object abuilder = builderClass.newInstance();
return (MBeanServerBuilder)abuilder;
......@@ -792,7 +792,7 @@ public class MBeanServerFactory {
String builderClassName = AccessController.doPrivileged(act);
try {
final Class newBuilderClass;
final Class<?> newBuilderClass;
if (builderClassName == null || builderClassName.length() == 0)
newBuilderClass = MBeanServerBuilder.class;
else
......@@ -800,7 +800,7 @@ public class MBeanServerFactory {
// Check whether a new builder needs to be created
if (builder != null) {
final Class builderClass = builder.getClass();
final Class<?> builderClass = builder.getClass();
if (newBuilderClass == builderClass)
return; // no need to create a new builder...
}
......
......@@ -39,11 +39,10 @@ public interface NotificationListener extends java.util.EventListener {
* blocking its notification broadcaster.
*
* @param notification The notification.
* @param handback An opaque object which helps the listener to associate information
* regarding the MBean emitter. This object is passed to the MBean during the
* addListener call and resent, without modification, to the listener. The MBean object
* should not use or modify the object.
*
* @param handback An opaque object which helps the listener to associate
* information regarding the MBean emitter. This object is passed to the
* addNotificationListener call and resent, without modification, to the
* listener.
*/
public void handleNotification(Notification notification, Object handback) ;
public void handleNotification(Notification notification, Object handback);
}
......@@ -26,7 +26,6 @@
package javax.management;
import com.sun.jmx.mbeanserver.NotificationMBeanSupport;
import com.sun.jmx.mbeanserver.Util;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
......@@ -43,6 +42,11 @@ import java.util.Set;
* on both the client and the server in the remote case, so using this class
* instead is recommended where possible.</p>
*
* <p>Because this class was introduced in version 2.0 of the JMX API,
* it may not be present on a remote JMX agent that is running an earlier
* version. The method {@link JMX#getSpecificationVersion
* JMX.getSpecificationVersion} can be used to determine the remote version.</p>
*
* <p>This class uses the {@linkplain Query Query API} to specify the
* filtering logic. For example, to select only notifications where the
* {@linkplain Notification#getType() type} is {@code "com.example.mytype"},
......
......@@ -27,7 +27,6 @@ package javax.management.event;
import java.io.IOException;
import java.util.concurrent.Executors; // for javadoc
import java.util.concurrent.ScheduledFuture;
/**
* This interface is used to specify a way to receive
......
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册