User: mulder
Date: 00/06/07 15:13:10
Modified: src/main/org/jboss/ejb/plugins/jrmp/interfaces
MethodInvocation.java
Log:
Fix the method lookup bug.
Revision Changes Path
1.6 +43 -43
jboss/src/main/org/jboss/ejb/plugins/jrmp/interfaces/MethodInvocation.java
Index: MethodInvocation.java
===================================================================
RCS file:
/products/cvs/ejboss/jboss/src/main/org/jboss/ejb/plugins/jrmp/interfaces/MethodInvocation.java,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- MethodInvocation.java 2000/06/04 23:19:01 1.5
+++ MethodInvocation.java 2000/06/07 22:13:09 1.6
@@ -15,83 +15,83 @@
import java.util.HashMap;
/**
- * MethodInvocation
+ * MethodInvocation
*
* This Serializable object carries the method to invoke and an identifier for the
target ojbect
- *
+ *
* @see <related>
* @author Rickard �berg ([EMAIL PROTECTED])
* @author <a href="mailto:[EMAIL PROTECTED]">Richard
Monson-Haefel</a>.
* @author <a href="mailto:[EMAIL PROTECTED]">Marc Fleury</a>.
- * @version $Revision: 1.5 $
+ * @version $Revision: 1.6 $
*/
public class MethodInvocation
implements java.io.Serializable
{
// Constants -----------------------------------------------------
-
+
// Attributes ----------------------------------------------------
Object id;
String className;
int hash = -9999;
Object[] args;
-
+
// Static --------------------------------------------------------
// MF FIXME: this is bad.
// It will grow quite large
// We need to work from the container context... not the server context it is
silly
static HashMap clazzMap = new HashMap();
-
+
static HashMap invokers = new HashMap(); // Prevent DGC
public static ContainerRemote getLocal(String jndiName) { return
(ContainerRemote)invokers.get(jndiName); }
public static void addLocal(String jndiName, ContainerRemote invoker) {
invokers.put(jndiName, invoker); }
public static void removeLocal(String jndiName) { invokers.remove(jndiName); }
-
+
// Constructors --------------------------------------------------
public MethodInvocation(Method m, Object[] args)
{
this(null, m, args);
}
-
+
public MethodInvocation(Object id, Method m, Object[] args)
{
this.id = id;
this.className = m.getDeclaringClass().getName();
- // m.hashCode only hashes on the name / class.
+ // m.hashCode only hashes on the name / class.
// Overriding is not seen and must include parameters
this.hash = calculateHash(m);
this.args = args;
-
+
System.out.println("In Method INVOCATION CREATE
"+m.getDeclaringClass()+m.getName()+m.getParameterTypes().length);
System.out.println("In Method INVOCATION CREATE hash "+hash);
-
+
}
// Public --------------------------------------------------------
-
-
+
+
public Object getId() { return id; }
-
+
/*
* MF FIXME: I am not sure this is a very good idea.
*
- * The use of the synchronized map is going to slow things down.
+ * The use of the synchronized map is going to slow things down.
* Also the penalty on the first invocation can be quite high.
* It is probably better to have the container pre-map the method.
- * We can then directly look up in the container and no need to
+ * We can then directly look up in the container and no need to
* extract the "method" from here, just the hashCode() (calculated one)
* In clear I am saying that this is overkill and slow. Will investigate.
*
* People will see this as they run their stuff for the first time (setup)
*/
- public Method getMethod()
+ public Method getMethod()
throws NoSuchMethodException, ClassNotFoundException
- {
+ {
HashMap methodMap;
Class clazz =
Thread.currentThread().getContextClassLoader().loadClass(className);
synchronized(clazzMap)
{
methodMap = (HashMap)clazzMap.get(clazz);
-
+
if (methodMap == null)
{
// Create method mapping
@@ -100,31 +100,31 @@
for (int i = 0; i < methods.length; i++)
{
System.out.println("Storing
"+methods[i].getDeclaringClass()+methods[i].getName()+methods[i].getParameterTypes().length+
" Hash "+calculateHash(methods[i]));
-
+
methodMap.put(new Integer(calculateHash(methods[i])), methods[i]);
}
clazzMap.put(clazz, methodMap);
}
}
-
+
synchronized(methodMap)
{
// Get method based on its hash value
Method m = (Method)methodMap.get(new Integer(hash));
System.out.println("In Method INVOCATION LOOKUP
"+m.getDeclaringClass()+m.getName()+m.getParameterTypes().length);
-
+
if (m == null)
throw new NoSuchMethodException(clazz+":"+hash);
return m;
}
}
-
- public Object[] getArguments()
+
+ public Object[] getArguments()
throws IOException, ClassNotFoundException
- {
+ {
return args;
}
-
+
/*
* The use of hashCode is not enough to differenciate methods
* we override the hashCode
@@ -132,31 +132,31 @@
* This is taken from the RMH code in EJBoss 0.9
*
*/
- public int calculateHash(Method method) {
-
- hash =
+ public static int calculateHash(Method method) {
+
+ int hash =
// We use the declaring class
method.getDeclaringClass().getName().hashCode() ^ //name of
class
// We use the name of the method
method.getName().hashCode(); //name of method
-
+
Class[] clazz = method.getParameterTypes();
-
+
for (int i = 0; i < clazz.length; i++) {
-
+
// XOR
- // We use the constant because
+ // We use the constant because
// a^b^b = a (thank you norbert)
// so that methodA() hashes to methodA(String, String)
-
+
hash = (hash +20000) ^ clazz[i].getName().hashCode();
}
-
+
return hash;
}
-
-
-
+
+
+
/*
* equals()
*
@@ -172,7 +172,7 @@
MethodInvocation other = (MethodInvocation)obj;
if(other.hash == this.hash) {
-
+
return true;
}
}
@@ -193,12 +193,12 @@
}
// Package protected ---------------------------------------------
-
+
// Protected -----------------------------------------------------
-
+
// Private -------------------------------------------------------
-
-
+
+
// Inner classes -------------------------------------------------
}