Add to Google Reader or Homepage

java.lang.illegalaccesserror

IllegalAccessError:

This java.lang.illegalAccessError is thrown when we try to access a private field,class or method.Usually this error is caught by compiler.If this error is thrown at run-rime then the class must be incompatibly changed.This is the reason why this error is a direct subclass of IncomaptibleClassChangeError.

This error commonly occurs when we use third-party libraries (external packages) in our application. Normally using  an external library in your application does not cause any error if it is compatible with the existing classes (more precisely existing binaries of those classes).

If it is incompatible with the existing binaries then an instance of sub class of IncompatibleClassChange Error will be thrown and specifically an instance of illegalAccessError will be thrown when we try to access a private field,method,class or interface.

See the following examples to have an idea about this error.

Program:

class C
{
static int c=20;
public void display(String a)
{
System.out.println(a);
}
}

class D extends C
{
public static void main(String args[])
{
c=45;
System.out.println(c);
C cobj=new C();
System.out.println(cobj.c);
cobj.display("Hello");
}
}

Let us analyze this program in detail to understand when this error will be thrown.If you compile and execute this program it will work fine.But if you change any field or method in class C to private and "recompile the class C alone" without recompiling all the classes at one shot then you will be left in a   awkward situation.

Note:

One thing i forgot to mention before is that this error will also occur when we try to modify the value of the field which is declared to be final.
So, it seems obvious that after all  this error is thrown  because of not recompiling the class files as a whole.Now,in order to find this error at compile-time you have to recompile all the class files at one shot.But at some occasions this error will not be identified even if you recompile all the classes and the reason is due to the availability of  two-different version of the package in the system.


Before explaining further i would like to tell you one thing that some peoples tends to place their  external packages(third-party libraries-usually an archive file) in the extension libraries and also in bootstrap libraries to avoid class path settings.

The remaining of this post is meant for those peoples Who may "accidentally" do like as follows?

Have a look at what am i going to do here? Here i have created three different version(1 original version as described above and two new Versions) of the class C as follows;

Version 1:

class C
{
private static int c=20;
private void display(String a)
{
System.out.println(a);
}
}
 

Here i have changed the access modifier of field c (static int c=20) and method display() into private.

Version2:

class C
{
final static int c=20;
public void display(String a)
{
System.out.println(a);
}
}

Here i have changed the type of field c into final.

Now i am going to pack these three different versions into three different jar files like pack1(original version),pack2(version 1),pack3 (version 2).

C:\blog>jar -cvf Pack1.jar C.class
added manifest
adding: C.class(in = 448) (out= 301)(deflated 32%)

C:\blog>jar -cvf Pack2.jar C.class
added manifest
adding: C.class(in = 448) (out= 300)(deflated 33%)

C:\blog>jar -cvf Pack3.jar C.class
added manifest
adding: C.class(in = 412) (out= 291)(deflated 29%)

Now if i place the Pack1.jar in jre/lib/ext and the Pack2.jar file in class path then while compiling the source file compiler will resolve the references using Pack1.jar since it is available in the extension library itself and as soon as the class file is found compiler will stop searching for classes further in class path.

During the launching of the applicationJVM also tends to search for class file in the class path as the reference in the archive file(located in the extension library) cannot be found by the JVM,because JVM only looks in jars that are"extensions of the java platform" and it will not search in user generated jars or third-party libraries.

So in this case JVM has no choice and it has to make use of the available reference (class C) in the Version 1  of the package that is pointed by class path.This is the reason why compiler does not show any error and the JVM shows this error during run-time.

Output:


C:\>cd blog

C:\blog>set classpath=c:\blog\Pack2.jar;c:\blog\Pack3.jar;

C:\blog>javac D.java

C:\blog>java D
Exception in thread "main" java.lang.IllegalAccessError: tried to access field C
.c from class D
        at D.main(D.java:5)





1 comments:

Anonymous said...

Thanks, this is generally helpful.
Still, I followed step-by-step your method in this Java online training
Java training

Post a Comment

 
java errors and exceptions © 2010 | Designed by Chica Blogger | Back to top