Project: AspectJ
Bug 119353 Inconsistent Implementations of ReferenceType.getDeclaredMethods()
Reported: 2005-12-05 23:11:15 | Status: resolved fixed

I am running into a problem in load-time weaving when I use reflection delegates because the weaver is generating an incorrect bridge method when I perform an inter-type declaration on Struts.ActionServlet for the init method. On investigation, the BCEL world is recognizing this as an overriding method, because its version of getDeclaredMethods is returning the declared methods for all ancestor superclasses. However, the reflection world is returning only the declared methods for this one class. It therefore appears that the weaver expects getDeclaredMethods to return all of them (making the name quite misleading). I think previously the method was being implemented inconsistently between 1.5 reflection and <1.5 reflection delegates. But it looks like it needs to be handled consistently to include all superclass methods. However, I dont know what other places (e.g., the MAP) are really expecting getDeclaredMethods and its siblings to behave like Java reflection's version... I started work on adding a getAllDeclaredMethods method to ReferenceType and delegates, as an alternative to provide the weaver the ability to check method overriding as in this case, but it's a little bit involved and I wanted to flag the issue first. Here's a test that fails and illustrates the issue: Index: ReflectionBasedReferenceTypeDelegateTest.java =================================================================== RCS file: /home/technology/org.aspectj/modules/weaver/testsrc/org/aspectj/weaver/reflect/ReflectionBasedReferenceTypeDelegateTest.java,v retrieving revision 1.5 diff -u -r1.5 ReflectionBasedReferenceTypeDelegateTest.java --- ReflectionBasedReferenceTypeDelegateTest.java 28 Nov 2005 17:44:40 -0000 1.5 +++ ReflectionBasedReferenceTypeDelegateTest.java 6 Dec 2005 04:11:41 -0000 @@ -238,6 +238,18 @@ assertTrue("Superclass for Map generic type should be Object but was "+rt2,rt2.equals(UnresolvedType.OBJECT)); } + public void testCompareSubclassDelegates() { + world.setBehaveInJava5Way(true); + + BcelWorld bcelWorld = new BcelWorld(); + bcelWorld.setBehaveInJava5Way(true); + UnresolvedType javaUtilHashMap = UnresolvedType.forName("java.util.HashMap"); + ReferenceType rawType = (ReferenceType)bcelWorld.resolve(javaUtilHashMap ); + + ReferenceType rawReflectType = (ReferenceType)world.resolve(javaUtilHashMap ); + assertEquals(rawType.getDelegate().getDeclaredMethods().length, rawReflectType.getDelegate().getDeclaredMethods().length); + } + // todo: array of int protected void setUp() throws Exception { This results in: junit.framework.AssertionFailedError: expected:<41> but was:<29> at junit.framework.Assert.fail(Assert.java:47) at junit.framework.Assert.failNotEquals(Assert.java:282) at junit.framework.Assert.assertEquals(Assert.java:64) at junit.framework.Assert.assertEquals(Assert.java:201) at junit.framework.Assert.assertEquals(Assert.java:207) at org.aspectj.weaver.reflect.ReflectionBasedReferenceTypeDelegateTest.testCompareSubclassDelegates(ReflectionBasedReferenceTypeDelegateTest.java:250) at java.lang.reflect.Method.invoke(Native Method) at junit.framework.TestCase.runTest(TestCase.java:154) at junit.framework.TestCase.runBare(TestCase.java:127) at junit.framework.TestResult$1.protect(TestResult.java:106) at junit.framework.TestResult.runProtected(TestResult.java:124) at junit.framework.TestResult.run(TestResult.java:109) at junit.framework.TestCase.run(TestCase.java:118) at junit.framework.TestSuite.runTest(TestSuite.java:208) at junit.framework.TestSuite.run(TestSuite.java:203) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:478) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:344) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:196)

Files changed in fix:
weaver/src/org/aspectj/weaver/reflect/ReflectionBasedReferenceTypeDelegateFactory.java weaver/testsrc/org/aspectj/weaver/reflect/ReflectionBasedReferenceTypeDelegateTest.java weaver5/java5-src/org/aspectj/weaver/reflect/Java15ReflectionBasedReferenceTypeDelegate.java