Community
Participate
Working Groups
The attached test case throws this error while executing using Eclipse 3.1 and AJDT 1.3.0
Created attachment 28736 [details] java and aj files and a JUnit test case to reproduce this java and aj files and a JUnit test case to reproduce this. I also think this bug might be a problem with my set up but it is recurring.
Not sure what error you get but I get IncompatibleClassChangeError when running the JUnit test program included. java.lang.IncompatibleClassChangeError at com.blueprint.util.aspectj5.test.PropertySupportAspect5.ajc$interMethodDispatch1$com_blueprint_util_aspectj5_test_PropertySupportAspect5$com_blueprint_util_aspectj5_test_PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5.aj) at com.blueprint.util.aspectj5.test.BeanTestCase.testPropertyChange(BeanTestCase.java:25) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) at java.lang.reflect.Method.invoke(Method.java:585) 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)
That's right. It is in the bug summary above.
Ah yes, ignore me - I'm suffering bugzilla blindness from looking at too many bugs. The supplied testcase also highlights an interesting problem with incremental compilation too.
The incremental compilation bug is there in my mixin pattern implementation that doesn't use annotations but it works there.
Do you have a workaround for this bug until it is fixed? Anything that would give me a annotation based mixin implementation.
I will look at this imminently and try to get you a workaround/fix - just need to finish another bug first.
testcase is checked into CVS (not the incremental compilation problem, just the IncompatibleClassChange problem).
I changed the retention policy on both annotations to RUNTIME and the code is working now. My initial assumption that the problem might be my set up seems to be true.
I noticed this morning that this was the problem too. I did append a note to bugzilla but it failed to attach correctly, grrrrr. Anyway, you should of course get a nice message when this happens, and I've just put support in for that: b.addPropertyChangeListener( "name", this ); ^^^^^^^^^^^^^^^^^^^^ BeanTestCase.java:18:0::0 The method addPropertyChangeListener(String, BeanTestCase) is undefined for the type Bean declare parents: @javaBean * implements PropertySupport; ^^^^^ PropertySupportAspect5.aj:9:0::0 Failing match because annotation 'javaBean' on type 'Bean' has SOURCE retention. Matching allowed when RetentionPolicy is CLASS or RUNTIME I'll check it in imminently.
For the sake of completeness I want to include my trip round the houses to discover the annotation was SOURCE (should have realised straightaway, doh!) === Exception in thread "main" java.lang.IncompatibleClassChangeError at PropertySupportAspect5.ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5.aj) at BeanTestCase.testPropertyChange(BeanTestCase.java:18) at BeanTestCase.main(BeanTestCase.java:13) line18 in BeanTestCase is: b.addPropertyChangeListener( "name", this ); which in the bytecode looks like this: PropertySupportAspect5.ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(b, "name", this); In PropertySupportAspect5 we find: public static void ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.beans.PropertyChangeListener); public static void ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.lang.String, java.beans.PropertyChangeListener); first one takes a propertysupport object and a propertychangelistener. second one takes a propertysupport object, a string and a propertychangelistener in this case we are calling the '2nd' one from BeanTestCase javap -verbose PropertySupport5 gives: public static void ajc$interMethod$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.beans.PropertyChangeListener); Code: Stack=0, Locals=2, Args_size=2 0: return public static void ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.beans.PropertyChangeListener); Code: Stack=2, Locals=2, Args_size=2 0: aload_0 1: aload_1 2: invokeinterface #53, 2; //InterfaceMethod PropertySupportAspect5$PropertySupport.addPropertyChangeListener:(Ljava/beans/PropertyChangeListener;)V 7: return public static void ajc$interMethod$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.lang.String, java.beans.PropertyChangeListener); Code: Stack=0, Locals=3, Args_size=3 0: return public static void ajc$interMethodDispatch1$PropertySupportAspect5$PropertySupportAspect5$PropertySupport$addPropertyChangeListener(PropertySupportAspect5$PropertySupport, java.lang.String, java.beans.PropertyChangeListener); Code: Stack=3, Locals=3, Args_size=3 0: aload_0 1: aload_1 2: aload_2 3: invokeinterface #59, 3; //InterfaceMethod PropertySupportAspect5$PropertySupport.addPropertyChangeListener:(Ljava/lang/String;Ljava/beans/PropertyChangeListener;)V 8: return In the case where we call the 3arg variant of ajc$<...>$addPropertyChangeListener() you can see that it calls PropertySupport5$PropertySupport.addPropertyChangeListener(PropertyChangeListener) In PropertySupportAspect5$PropertySupport we see: public abstract void addPropertyChangeListener(java.beans.PropertyChangeListener); public abstract void addPropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener); And in 'Bean' which is declare parents'd to implement that interface we see: public class Bean extends java.lang.Object implements java.io.Serializable{ private java.lang.String name; public Bean(); public java.lang.String getName(); public void setName(java.lang.String); } errrrrr! It's missing. Bean should be marked as implementing PropertySupport and it should have the default implementations from the aspect stuffed into it. So, you get IncompatibleClassChangeError. First, lets turn on showWeaveInfo to see what it says: Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.hasListeners(java.lang.String)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.firePropertyChange(Bean, java.lang.String, java.lang.String, java.lang.String)') Interestingly there is *nothing* about the declare parents working. Let's change the decp statement to explicitly target Bean. Extending interface set for type 'Bean' (Bean.java) to include 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.beans.PropertyChangeListener)') Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.beans.PropertyChangeListener)') Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.hasListeners(java.lang.String)') Type 'Bean' (Bean.java) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.firePropertyChange(Bean, java.lang.String, java.lang.String, java.lang.String)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.addPropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.lang.String, java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.removePropertyChangeListener(java.beans.PropertyChangeListener)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.hasListeners(java.lang.String)') Type 'PropertySupportAspect5$PropertySupport' (PropertySupportAspect5.aj) has intertyped method from 'PropertySupportAspect5' (PropertySupportAspect5.aj:'void PropertySupportAspect5$PropertySupport.firePropertyChange(Bean, java.lang.String, java.lang.String, java.lang.String)') You can see Bean gets a lot more action now and the testcase runs fine. So the question is why '@javaBean *' didn't appear to match the Bean type in some ways but did in others... Breakpoint in DeclareParents.maybeGetNewParent() - what does it think? It is called during AjLookupEnvironment.completeTypeBindings() (i.e. during compilation) - it succeeds and returns PropertySupportAspect5$PropertySupport In BcelWeaver we also do the declare parents (for the case of binary weaving). Here the match fails and the decp doesn't apply. Why is that? Well it turns out that the annotation has SOURCE retention so of course it is lost and never put into the bytecode. So the fix is for us to put out an message if you attempt to match on a SOURCE annotation.
Fix checked in to give the nice new messages. Will close when build available.
Fix available - i believe incremental case is a symptom of the same problem. Please reopen if you still see a problem with the incremental compilation.