Bug 128237 - [@AspectJ] NPE on @AJ code with pointcut which contains logical OR operation.
Summary: [@AspectJ] NPE on @AJ code with pointcut which contains logical OR operation.
Status: RESOLVED FIXED
Alias: None
Product: AspectJ
Classification: Tools
Component: Compiler (show other bugs)
Version: 1.5.0   Edit
Hardware: PC Linux
: P3 blocker (vote)
Target Milestone: 1.5.1   Edit
Assignee: aspectj inbox CLA
QA Contact:
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2006-02-16 11:21 EST by Eugene Kireyev CLA
Modified: 2012-04-03 15:50 EDT (History)
0 users

See Also:


Attachments
patch containing failing testcase (2.55 KB, patch)
2006-02-17 06:51 EST, Helen Beeken CLA
aclement: iplog+
Details | Diff
patch containing proposed fix (898 bytes, patch)
2006-02-17 06:57 EST, Helen Beeken CLA
aclement: iplog+
Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Eugene Kireyev CLA 2006-02-16 11:21:26 EST
I got NullPointerException during compilation of any @AspectJ code with pointcut which contains logical OR operation.

-----Here is my test case for this bug----------------

import java.io.IOException;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;

@Aspect
class AbstractTracer 
{
	@Pointcut("(execution(public * Foo+.* (..)) || execution(public * Foo+.blablabla (..)))&& !execution(public Foo+.new (..))")
//	@Pointcut("(execution(public * Foo+.* (..)))&& !execution(public Foo+.new (..))")
	protected void methodCall(){};

	@Pointcut("methodCall()&& this(obj)")
	private void objectCall(Object obj) {
	};

	@Around("objectCall(obj)")
	public Object aroundMethodCall(ProceedingJoinPoint thisJoinPoint,
			Object obj) throws Throwable {
		System.out.println("Before "+thisJoinPoint.getSignature().toString());
		if ( thisJoinPoint.getSignature().toString().indexOf("A")!= -1)
		{
			throw new IOException("Hello from Aspect!");
//			throw new Exception("Hello from Aspect!");
		}
		Object result = thisJoinPoint.proceed();
		System.out.println("After "+thisJoinPoint.getSignature().toString());
		return result;
	}

}


public class Foo {
	public void methodA() throws IOException {
		throw new IOException("Foo.methodA");
	}

	public void methodB(boolean b) throws Exception
	{
		if ( b )
		{
			throw new Exception("Foo.methodB");
		}
	}
	/**
	 * @param args
	 */
	public static void main(String[] args) {
		Foo obj = new Foo();
		try
		{
			obj.methodA();
			System.out.println("Something going wrong!");
		}
		catch ( IOException e)
		{
			System.out.println("All right! We got exception");
			e.printStackTrace(System.out);
		}
		try
		{
			obj.methodB(false);
			System.out.println("All right!");
		}
		catch ( Exception e)
		{
			System.out.println("Something going wrong! We got exception");
			e.printStackTrace(System.out);
		}
		
	}

}

------------------------------------------------------

and here is acj error log
------------------------------------------------------
---- AspectJ Properties ---
AspectJ Compiler 1.5.0 built on Tuesday Dec 20, 2005 at 12:05:54 GMT
---- Dump Properties ---
Dump file: ajcore.20060216.175147.608.txt
Dump reason: java.lang.NullPointerException
Dump on exception: true
Dump at exit condition: abort
---- Exception Information ---
java.lang.NullPointerException
	at org.aspectj.weaver.bcel.BcelWeaver.validateOrBranch(BcelWeaver.java:611)
	at org.aspectj.weaver.bcel.BcelWeaver.validateBindings(BcelWeaver.java:579)
	at org.aspectj.weaver.bcel.BcelWeaver.rewritePointcuts(BcelWeaver.java:511)
	at org.aspectj.weaver.bcel.BcelWeaver.prepareForWeave(BcelWeaver.java:449)
	at org.aspectj.ajdt.internal.compiler.AjCompilerAdapter.weave(AjCompilerAdapter.java:283)
	at org.aspectj.ajdt.internal.compiler.AjCompilerAdapter.afterCompiling(AjCompilerAdapter.java:178)
	at org.aspectj.ajdt.internal.compiler.CompilerAdapter.ajc$afterReturning$org_aspectj_ajdt_internal_compiler_CompilerAdapter$2$f9cc9ca0(CompilerAdapter.aj:70)
	at org.aspectj.org.eclipse.jdt.internal.compiler.Compiler.compile(Compiler.java:367)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.performCompilation(AjBuildManager.java:811)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.doBuild(AjBuildManager.java:230)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.batchBuild(AjBuildManager.java:156)
	at org.aspectj.ajdt.ajc.AjdtCommand.doCommand(AjdtCommand.java:112)
	at org.aspectj.ajdt.ajc.AjdtCommand.runCommand(AjdtCommand.java:60)
	at org.aspectj.tools.ajc.Main.run(Main.java:326)
	at org.aspectj.tools.ajc.Main.runMain(Main.java:240)
	at org.aspectj.tools.ajc.Main.main(Main.java:83)
---- System Properties ---
java.runtime.name=Java(TM) 2 Runtime Environment, Standard Edition
sun.boot.library.path=/opt/Java/jdk1.5.0_04/jre/lib/i386
java.vm.version=1.5.0_04-b05
java.vm.vendor=Sun Microsystems Inc.
java.vendor.url=http://java.sun.com/
path.separator=:
java.vm.name=Java HotSpot(TM) Client VM
file.encoding.pkg=sun.io
user.country=RU
sun.os.patch.level=unknown
java.vm.specification.name=Java Virtual Machine Specification
user.dir=/home/kei/ajdt-workspace/AspectJTests
java.runtime.version=1.5.0_04-b05
java.awt.graphicsenv=sun.awt.X11GraphicsEnvironment
java.endorsed.dirs=/opt/Java/jdk1.5.0_04/jre/lib/endorsed
os.arch=i386
java.io.tmpdir=/tmp
line.separator=

java.vm.specification.vendor=Sun Microsystems Inc.
os.name=Linux
sun.jnu.encoding=UTF-8
java.library.path=/opt/Java/jdk1.5.0_04/jre/lib/i386/client:/opt/Java/jdk1.5.0_04/jre/lib/i386:/opt/Java/jdk1.5.0_04/jre/../lib/i386:.:
java.specification.name=Java Platform API Specification
java.class.version=49.0
sun.management.compiler=HotSpot Client Compiler
os.version=2.6.15-1.1831_FC4
user.home=/home/kei
user.timezone=Europe/Kiev
java.awt.printerjob=sun.print.PSPrinterJob
file.encoding=UTF-8
java.specification.version=1.5
java.class.path=components/aspectjweaver.jar:components/aspectjtools.jar:components/aspectjrt.jar:components/aspectjlib.jar:/build/auroratest.jar:/opt/Java/aspectj1.5/lib/aspectjtools.jar:/opt/Java/jdk1.5.0_04/lib/tools.jar
user.name=kei
java.vm.specification.version=1.0
java.home=/opt/Java/jdk1.5.0_04/jre
sun.arch.data.model=32
user.language=ru
java.specification.vendor=Sun Microsystems Inc.
java.vm.info=mixed mode, sharing
java.version=1.5.0_04
java.ext.dirs=/opt/Java/jdk1.5.0_04/jre/lib/ext
sun.boot.class.path=/opt/Java/jdk1.5.0_04/jre/lib/rt.jar:/opt/Java/jdk1.5.0_04/jre/lib/i18n.jar:/opt/Java/jdk1.5.0_04/jre/lib/sunrsasign.jar:/opt/Java/jdk1.5.0_04/jre/lib/jsse.jar:/opt/Java/jdk1.5.0_04/jre/lib/jce.jar:/opt/Java/jdk1.5.0_04/jre/lib/charsets.jar:/opt/Java/jdk1.5.0_04/jre/classes
java.vendor=Sun Microsystems Inc.
file.separator=/
java.vendor.url.bug=http://java.sun.com/cgi-bin/bugreport.cgi
sun.io.unicode.encoding=UnicodeLittle
sun.cpu.endian=little
sun.cpu.isalist=
---- Command Line ---
-1.5
Foo.java
---- Full Classpath ---
/opt/Java/jdk1.5.0_04/jre/lib/rt.jar(39713589 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/i18n.jar(missing)
/opt/Java/jdk1.5.0_04/jre/lib/sunrsasign.jar(missing)
/opt/Java/jdk1.5.0_04/jre/lib/jsse.jar(549315 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/jce.jar(81799 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/charsets.jar(8627836 bytes)
/opt/Java/jdk1.5.0_04/jre/classes(missing)
/opt/Java/jdk1.5.0_04/jre/lib/ext/localedata.jar(802502 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/sunpkcs11.jar(175414 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/dnsns.jar(8176 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/sunjce_provider.jar(153235 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bctsp-jdk15-129.jar(38357 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcprov-jdk15-129.jar(1168795 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3daudio.jar(1386793 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcmail-jdk15-129.jar(124831 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3dcore.jar(2514820 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3dutils.jar(1401997 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/vecmath.jar(290018 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcprov-jdk14-129.jar(1157625 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcmail-jdk14-129.jar(126679 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjweaver.jar(1746917 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjrt.jar(108647 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjlib.jar(7845 bytes)
/build/auroratest.jar(missing)
/opt/Java/jdk1.5.0_04/lib/tools.jar(7015499 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/localedata.jar(802502 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/sunpkcs11.jar(175414 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/dnsns.jar(8176 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/sunjce_provider.jar(153235 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bctsp-jdk15-129.jar(38357 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcprov-jdk15-129.jar(1168795 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3daudio.jar(1386793 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcmail-jdk15-129.jar(124831 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3dcore.jar(2514820 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/j3dutils.jar(1401997 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/vecmath.jar(290018 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcprov-jdk14-129.jar(1157625 bytes)
/opt/Java/jdk1.5.0_04/jre/lib/ext/bcmail-jdk14-129.jar(126679 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjweaver.jar(1746917 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjrt.jar(108647 bytes)
/home/kei/ajdt-workspace/AspectJTests/components/aspectjlib.jar(7845 bytes)
/build/auroratest.jar(missing)
/opt/Java/jdk1.5.0_04/lib/tools.jar(7015499 bytes)
---- Compiler Messages ---
abort ABORT -- (NullPointerException) null
null
java.lang.NullPointerException
	at org.aspectj.weaver.bcel.BcelWeaver.validateOrBranch(BcelWeaver.java:611)
	at org.aspectj.weaver.bcel.BcelWeaver.validateBindings(BcelWeaver.java:579)
	at org.aspectj.weaver.bcel.BcelWeaver.rewritePointcuts(BcelWeaver.java:511)
	at org.aspectj.weaver.bcel.BcelWeaver.prepareForWeave(BcelWeaver.java:449)
	at org.aspectj.ajdt.internal.compiler.AjCompilerAdapter.weave(AjCompilerAdapter.java:283)
	at org.aspectj.ajdt.internal.compiler.AjCompilerAdapter.afterCompiling(AjCompilerAdapter.java:178)
	at org.aspectj.ajdt.internal.compiler.CompilerAdapter.ajc$afterReturning$org_aspectj_ajdt_internal_compiler_CompilerAdapter$2$f9cc9ca0(CompilerAdapter.aj:70)
	at org.aspectj.org.eclipse.jdt.internal.compiler.Compiler.compile(Compiler.java:367)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.performCompilation(AjBuildManager.java:811)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.doBuild(AjBuildManager.java:230)
	at org.aspectj.ajdt.internal.core.builder.AjBuildManager.batchBuild(AjBuildManager.java:156)
	at org.aspectj.ajdt.ajc.AjdtCommand.doCommand(AjdtCommand.java:112)
	at org.aspectj.ajdt.ajc.AjdtCommand.runCommand(AjdtCommand.java:60)
	at org.aspectj.tools.ajc.Main.run(Main.java:326)
	at org.aspectj.tools.ajc.Main.runMain(Main.java:240)
	at org.aspectj.tools.ajc.Main.main(Main.java:83)

---- org.aspectj.weaver.bcel.BcelWorld ----
Shadow mungers:
(around(extraFlags: 2): (persingleton(AbstractTracer) && (((execution(public * Foo+.*(..)) || execution(public * Foo+.blablabla(..))) && !execution(public Foo+.new(..))) && this(BindingTypePattern(java.lang.Object, 1))))->java.lang.Object AbstractTracer.aroundMethodCall(org.aspectj.lang.ProceedingJoinPoint, java.lang.Object))
Type mungers:
(BcelTypeMunger null)
(BcelTypeMunger ResolvedTypeMunger(PrivilegedAccess, void java.lang.Object.()))
Late Type mungers:
(BcelTypeMunger null)
------------------------------------------------------------------

I got same error with latest (aspectj-DEVELOPMENT-20060216105006) night build.
Comment 1 Helen Beeken CLA 2006-02-17 05:15:23 EST
For this bug to materialize we require the following:

* a pointcut of the form "(pc1 || pc2) && this(Type)" where pc1 includes a wildcard
* advice which uses the Type in "this" and also has the extra argument required for use of JoinPoint. 

i.e.:

    @Pointcut("(execution(public * Foo.anotherMethod*(..)) || execution(public * 
                Foo.methodA(..))) && this(obj)")
    protected void methodExec(Object obj){};
        
    @Before("methodExec(obj)")
    public void beforeMethodExec(JoinPoint thisJoinPoint, Object obj) {
      	System.out.println("Before " + thisJoinPoint.getSignature().toString());
    }
Comment 2 Helen Beeken CLA 2006-02-17 06:51:52 EST
Created attachment 34907 [details]
patch containing failing testcase

Apply this patch to the tests project.
Comment 3 Helen Beeken CLA 2006-02-17 06:57:21 EST
Created attachment 34908 [details]
patch containing proposed fix

Apply to the weaver project.

When rewritten the pointcut becomes

LHS = (execution(public * Foo.anotherMethod*(..)) && this(BindingTypePattern(java.lang.Object,1))) && persingleton(AbstractTracer)

RHS = (execution(public * Foo.methodA(..)) && this(BindingTypePattern(java.lang.Object,1))) && persingleton(AbstractTracer)

When we come to see if the LHS and RHS could ever match the same join points we return true. If the wildcard isn't there this returns false. Because it's true we then check the name of the binding associated with the LHS with that associated with the RHS. If they're not equal then we add this to the list of ambiguousNames and raise an error. This is where the NPE is coming from because the binding associated with the LHS is null.

The reason we're failing here with the @AJ aspect in comment #1 is the addition of the "thisJoinPoint" in the method signature. When we come to validate the bindings we include this extra argument. Consequently, the array of bindings has 2 entries rather than 1. We find the BindingTypePattern(java.lang.Object,1)) and enter this as the second entry in the array of bindings. However, there aren't any others so the first entry in the array of bindings remains null. This causes the NPE when we ask if it's name is the same as the corresponding entry for the RHS (which is also null).

I think it's reasonable to add a null check here. If the entry in the LHS array of bindings is null then add the corresponding name to the list of ambiguousNames iff the corresponding entry in the RHS array of bindings isn't null. If they're both null then this is ok.
Comment 4 Andrew Clement CLA 2006-02-21 10:55:14 EST
fix committed.
Comment 5 Andrew Clement CLA 2006-02-22 04:04:23 EST
fix available