00001 package gov.nasa.arc.ase.jpf.jvm.reflection;
00002
00003 import gov.nasa.arc.ase.jpf.InternalErrorException;
00004 import gov.nasa.arc.ase.jpf.iThreadInfo;
00005 import gov.nasa.arc.ase.jpf.jvm.*;
00006 import gov.nasa.arc.ase.jpf.jvm.bytecode.Instruction;
00007
00008 public class JavaLangObjectReflection extends Reflection {
00009 public Instruction executeMethod(MethodInfo mi) {
00010 String name = mi.getFullName();
00011
00012 if(name.equals("clone()Ljava/lang/Object;")) {
00013
00014 throw new NativeMethodException("clone()Ljava/lang/Object;");
00015 }
00016
00017 if(name.equals("getClass()Ljava/lang/Class;")) {
00018
00019 throw new NativeMethodException("getClass()Ljava/lang/Class;");
00020 }
00021
00022 if(name.equals("hashCode()I")) {
00023 return exit(objref ^ 0xABCD);
00024 }
00025
00026 if(name.equals("notify()V")) {
00027 da.get(objref).notifies();
00028
00029 return exit();
00030 }
00031
00032 if(name.equals("notifyAll()V")) {
00033 da.get(objref).notifiesAll();
00034
00035 return exit();
00036 }
00037
00038 if(name.equals("wait(J)V")) {
00039 long length = getLongArgument(0);
00040 boolean timeout = false;
00041
00042 if(length != 0)
00043 timeout = ss.random(2) == 0;
00044
00045 if(timeout)
00046 return exit();
00047 else {
00048 if (th.getStatus() == iThreadInfo.RUNNING) {
00049 da.get(objref).wait(th);
00050 return repeat();
00051 } else if(th.getStatus() == iThreadInfo.NOTIFIED) {
00052 da.get(objref).lockNotified(th);
00053
00054 return exit();
00055 } else if(th.getStatus() == iThreadInfo.INTERRUPTED) {
00056 da.get(objref).lockNotified(th);
00057
00058 return throwException("java.lang.InterruptedException");
00059 } else
00060 throw new InternalErrorException("invalid thread state");
00061 }
00062 }
00063
00064 if(name.equals("wait()V")) {
00065 if (th.getStatus() == iThreadInfo.RUNNING) {
00066 da.get(objref).wait(th);
00067
00068 return repeat();
00069 } else if(th.getStatus() == iThreadInfo.NOTIFIED) {
00070 da.get(objref).lockNotified(th);
00071
00072 return exit();
00073 } else if(th.getStatus() == iThreadInfo.INTERRUPTED) {
00074 da.get(objref).lockNotified(th);
00075
00076 return throwException("java.lang.InterruptedException");
00077 } else
00078 throw new InternalErrorException("invalid thread state");
00079 }
00080
00081 return super.executeMethod(mi);
00082 }
00083 public Instruction executeStaticMethod(MethodInfo mi) {
00084 String name = mi.getFullName();
00085
00086 if(name.equals("registerNatives()V"))
00087 return exit();
00088
00089 return super.executeStaticMethod(mi);
00090 }
00091 public boolean isMethodDeterministic(MethodInfo mi) {
00092 String name = mi.getFullName();
00093
00094 if(name.equals("notify()V")) {
00095 return false;
00096 }
00097
00098 if(name.equals("clone()Ljava/lang/Object;")) {
00099
00100 throw new NativeMethodException("clone()Ljava/lang/Object;");
00101 }
00102
00103 if(name.equals("getClass()Ljava/lang/Class;")) {
00104
00105 throw new NativeMethodException("getClass()Ljava/lang/Class;");
00106 }
00107
00108 if(name.equals("wait(J)V")) {
00109 long length = getLongArgument(0);
00110
00111 return length == 0;
00112 }
00113
00114 return super.isMethodDeterministic(mi);
00115 }
00116 public boolean isMethodExecutable(MethodInfo mi) {
00117 String name = mi.getFullName();
00118
00119 if(name.equals("clone()Ljava/lang/Object;")) {
00120
00121 throw new NativeMethodException("clone()Ljava/lang/Object;");
00122 }
00123
00124 if(name.equals("getClass()Ljava/lang/Class;")) {
00125
00126 throw new NativeMethodException("getClass()Ljava/lang/Class;");
00127 }
00128
00129 if(name.equals("wait(J)V")) {
00130 long length = getLongArgument(0);
00131 boolean timeout = false;
00132
00133 if(length != 0)
00134 timeout = ss.random(2) == 0;
00135
00136 if(timeout)
00137 return true;
00138 else if (th.getStatus() == iThreadInfo.RUNNING)
00139 return true;
00140 else if(th.getStatus() == iThreadInfo.NOTIFIED)
00141 return da.get(objref).canLock(th);
00142 else if(th.getStatus() == iThreadInfo.INTERRUPTED)
00143 return da.get(objref).canLock(th);
00144 else
00145 throw new InternalErrorException("invalid thread state");
00146 }
00147
00148 if(name.equals("wait()V")) {
00149 if (th.getStatus() == iThreadInfo.RUNNING)
00150 return true;
00151 else if(th.getStatus() == iThreadInfo.NOTIFIED)
00152 return da.get(objref).canLock(th);
00153 else if(th.getStatus() == iThreadInfo.INTERRUPTED)
00154 return da.get(objref).canLock(th);
00155 else
00156 return false;
00157 }
00158
00159 return super.isMethodExecutable(mi);
00160 }
00161 public boolean isStaticMethodDeterministic(MethodInfo mi) {
00162 String name = mi.getFullName();
00163
00164 return super.isStaticMethodDeterministic(mi);
00165 }
00166 public boolean isStaticMethodExecutable(MethodInfo mi) {
00167 String name = mi.getFullName();
00168
00169 return super.isStaticMethodExecutable(mi);
00170 }
00171 }