*** empty log message ***

git-svn-id: https://svn.code.sf.net/p/jode/code/trunk@49 379699f6-c40d-0410-875b-85095c16579e
stable
jochen 26 years ago
parent 1339141e8e
commit 2d1648439c
  1. 341
      jode/jode/type/ClassInterfacesType.java

@ -35,41 +35,62 @@ import java.util.Stack;
* @author Jochen Hoenicke */
public class ClassInterfacesType extends MyType {
ClassDeclaration clazz;
ClassDeclaration ifaces[];
Class clazz;
Class ifaces[];
public final static Class cObject = new Object().getClass();
public ClassInterfacesType(Type clazzType) {
super(104, "{"+clazzType.getTypeSignature()+"}");
ClassDeclaration cdecl =
new ClassDeclaration(clazzType.getClassName());
try {
if (cdecl.getClassDefinition(env).isInterface()) {
clazz = new ClassDeclaration(Constants.idJavaLangObject);
ifaces = new ClassDeclaration[1];
Class cdecl =
Class.forName(clazzType.getClassName().toString());
if (cdecl.isInterface()) {
clazz = cObject;
ifaces = new Class[1];
ifaces[0] = cdecl;
} else {
clazz = cdecl;
ifaces = new ClassDeclaration[0];
ifaces = new Class[0];
}
} catch (ClassNotFound ex) {
} catch (ClassNotFoundException ex) {
throw new AssertError(ex.toString());
}
}
public ClassInterfacesType(ClassDeclaration clazz,
ClassDeclaration[] ifaces) {
public ClassInterfacesType(Class clazz,
Class[] ifaces) {
super(104, "{}");
StringBuffer sig = new StringBuffer("{");
if (clazz != null)
sig.append(clazz.getType().getTypeSignature());
sig.append("L").append(clazz.getName()).append(";");
for (int i=0;i < ifaces.length; i++)
sig.append(ifaces[i].getType().getTypeSignature());
sig.append("L").append(ifaces[i].getName()).append(";");
sig.append("}");
typeSig = sig.toString();
this.clazz = clazz;
this.ifaces = ifaces;
}
public final static boolean superClassOf(Class parent, Class clazz) {
while (clazz != parent && clazz != null) {
clazz = clazz.getSuperclass();
}
return clazz == parent;
}
public final static boolean implementedBy(Class iface, Class clazz) {
while (clazz != iface && clazz != null) {
Class[] ifaces = clazz.getInterfaces();
for (int i=0; i< ifaces.length; i++) {
if (implementedBy(iface, ifaces[i]))
return true;
}
clazz = clazz.getSuperclass();
}
return clazz != null;
}
/**
* Checks if the given type range may be not empty.
* This means, that bottom.clazz is extended by top.clazz
@ -81,65 +102,55 @@ public class ClassInterfacesType extends MyType {
*/
public final static Type createRangeType(ClassInterfacesType bottom,
ClassInterfacesType top) {
try {
if (bottom.clazz != null
&& bottom.clazz.getType() != tObject) {
/* The searched type must be a class type.
*/
if (top.ifaces.length != 0
|| !bottom.clazz.getClassDefinition(env).
superClassOf(env,top.clazz))
if (bottom.clazz != null
&& bottom.clazz != cObject) {
/* The searched type must be a class type.
*/
if (top.ifaces.length != 0
|| !superClassOf(bottom.clazz,top.clazz))
return tError;
/* All interfaces must be implemented by top.clazz
*/
for (int i=0; i < bottom.ifaces.length; i++) {
if (!implementedBy(bottom.ifaces[i], top.clazz))
return tError;
/* All interfaces must be implemented by top.clazz
*/
for (int i=0; i < bottom.ifaces.length; i++) {
if (!bottom.ifaces[i].getClassDefinition(env).
implementedBy(env,top.clazz))
return tError;
}
return new ClassRangeType
(bottom, new ClassInterfacesType(top.clazz,
new ClassDeclaration[0]));
} else {
return new ClassRangeType
(bottom, new ClassInterfacesType(top.clazz,
new Class[0]));
/* Now bottom.clazz is null, find all top.class/interfaces
* that implement all bottom.ifaces.
*/
ClassDeclaration clazz = top.clazz;
if (clazz != null) {
for (int i=0; i < bottom.ifaces.length; i++) {
ClassDefinition idef =
bottom.ifaces[i].getClassDefinition(env);
if (!idef.implementedBy(env, clazz)) {
clazz = null;
break;
}
} else {
/* Now bottom.clazz is null, find all top.class/interfaces
* that implement all bottom.ifaces.
*/
Class clazz = top.clazz;
if (clazz != null) {
for (int i=0; i < bottom.ifaces.length; i++) {
if (!implementedBy(bottom.ifaces[i], clazz)) {
clazz = null;
break;
}
}
Vector ifaces = new Vector();
big_loop:
for (int j=0; j < top.ifaces.length; j++) {
for (int i=0; i < bottom.ifaces.length; i++) {
ClassDefinition idef =
bottom.ifaces[i].getClassDefinition(env);
if (!idef.implementedBy(env, top.ifaces[j]))
continue big_loop;
}
ifaces.addElement(top.ifaces[j]);
}
Vector ifaces = new Vector();
big_loop:
for (int j=0; j < top.ifaces.length; j++) {
for (int i=0; i < bottom.ifaces.length; i++) {
if (!implementedBy(bottom.ifaces[i], top.ifaces[j]))
continue big_loop;
}
ClassDeclaration[] ifaceArray =
new ClassDeclaration[ifaces.size()];
ifaces.addElement(top.ifaces[j]);
}
Class[] ifaceArray =
new Class[ifaces.size()];
ifaces.copyInto(ifaceArray);
return new ClassRangeType
(bottom, new ClassInterfacesType(clazz, ifaceArray));
}
} catch (ClassNotFound ex) {
return tError;
}
}
}
/**
* Returns the specialized type of t1 and t2.
* We have two classes and multiple interfaces. The result
@ -149,77 +160,68 @@ public class ClassInterfacesType extends MyType {
public static Type getSpecializedType(ClassInterfacesType t1,
ClassInterfacesType t2) {
ClassDeclaration clazz = null;
Class clazz = null;
Vector ifaces = new Vector();
/* First determine the clazz, one of the two classes must be a sub
* class of the other or null.
*/
try {
if (t1.clazz == null)
clazz = t2.clazz;
else if (t2.clazz == null)
clazz = t1.clazz;
else if (t1.clazz.
getClassDefinition(env).superClassOf(env, t2.clazz))
clazz = t2.clazz;
else if (t2.clazz.
getClassDefinition(env).superClassOf(env, t1.clazz))
clazz = t1.clazz;
else
return tError;
/* The interfaces are simply the union of both interfaces set.
* But we can simplify this, if an interface is implemented by
* another or by the class, we can omit it.
*/
big_loop_t1:
for (int i=0; i< t1.ifaces.length; i++) {
ClassDeclaration iface = t1.ifaces[i];
ClassDefinition idef = iface.getClassDefinition(env);
if (clazz != null && idef.implementedBy(env, clazz)) {
if (t1.clazz == null)
clazz = t2.clazz;
else if (t2.clazz == null)
clazz = t1.clazz;
else if (superClassOf(t1.clazz, t2.clazz))
clazz = t2.clazz;
else if (superClassOf(t2.clazz, t1.clazz))
clazz = t1.clazz;
else
return tError;
/* The interfaces are simply the union of both interfaces set.
* But we can simplify this, if an interface is implemented by
* another or by the class, we can omit it.
*/
big_loop_t1:
for (int i=0; i< t1.ifaces.length; i++) {
Class iface = t1.ifaces[i];
if (clazz != null && implementedBy(iface, clazz)) {
continue big_loop_t1;
}
for (int j=0; j<t2.ifaces.length; j++) {
if (implementedBy(iface, t2.ifaces[j])) {
continue big_loop_t1;
}
for (int j=0; j<t2.ifaces.length; j++) {
if (idef.implementedBy(env, t2.ifaces[j])) {
continue big_loop_t1;
}
}
}
/* This interface is not implemented by any of the other
* ifaces. Add it to the interfaces vector.
*/
ifaces.addElement(iface);
/* This interface is not implemented by any of the other
* ifaces. Add it to the interfaces vector.
*/
ifaces.addElement(iface);
}
big_loop_t2:
for (int i=0; i< t2.ifaces.length; i++) {
Class iface = t2.ifaces[i];
if (clazz != null && implementedBy(iface, clazz)) {
continue big_loop_t2;
}
big_loop_t2:
for (int i=0; i< t2.ifaces.length; i++) {
ClassDeclaration iface = t2.ifaces[i];
ClassDefinition idef = iface.getClassDefinition(env);
if (clazz != null && idef.implementedBy(env, clazz)) {
for (int j=0; j<ifaces.size(); j++) {
if (implementedBy(iface, (Class) ifaces.elementAt(j))) {
continue big_loop_t2;
}
for (int j=0; j<ifaces.size(); j++) {
if (idef.implementedBy
(env, (ClassDeclaration) ifaces.elementAt(j))) {
continue big_loop_t2;
}
}
/* This interface is not implemented by any of the other
* ifaces. Add it to the interfaces vector.
*/
ifaces.addElement(iface);
}
if (clazz.getType() == tObject && ifaces.size() > 0)
/* Every interface implies tObject, so remove it */
clazz = null;
} catch (ClassNotFound ex) {
return tError;
}
ClassDeclaration[] ifaceArray = new ClassDeclaration[ifaces.size()];
/* This interface is not implemented by any of the other
* ifaces. Add it to the interfaces vector.
*/
ifaces.addElement(iface);
}
if (clazz == cObject && ifaces.size() > 0)
/* Every interface implies tObject, so remove it */
clazz = null;
Class[] ifaceArray = new Class[ifaces.size()];
ifaces.copyInto(ifaceArray);
return new ClassInterfacesType(clazz, ifaceArray);
}
@ -234,81 +236,77 @@ public class ClassInterfacesType extends MyType {
public static Type getGeneralizedType(ClassInterfacesType t1,
ClassInterfacesType t2) {
ClassDeclaration clazz;
Class clazz;
Vector ifaces = new Vector();
try {
/* First the easy part, determine the clazz */
if (t1.clazz == null)
clazz = t2.clazz;
else if (t2.clazz == null)
clazz = t1.clazz;
else {
clazz = t1.clazz;
/* First the easy part, determine the clazz */
if (t1.clazz == null)
clazz = t2.clazz;
else if (t2.clazz == null)
clazz = t1.clazz;
else {
clazz = t1.clazz;
while(clazz != null) {
ClassDefinition cdef = clazz.getClassDefinition(env);
if (cdef.superClassOf(env, t2.clazz))
break;
clazz = cdef.getSuperClass(env);
}
if (clazz.getType() == tObject)
clazz = null;
while(clazz != null) {
if (superClassOf(clazz, t2.clazz))
break;
clazz = clazz.getSuperclass();
}
if (clazz == cObject)
clazz = null;
}
/* Now the more complicated part: find all interfaces, that are
/* Now the more complicated part: find all interfaces, that are
* implemented by one interface or class in each group.
*
* First get all interfaces of t1.clazz and t1.ifaces.
*/
Stack allIfaces = new Stack();
if (t1.clazz != null) {
ClassDeclaration clazzIfaces[] =
t1.clazz.getClassDefinition(env).getInterfaces();
Stack allIfaces = new Stack();
if (t1.clazz != null) {
Class c = t1.clazz;
while (clazz != c) {
Class clazzIfaces[] = c.getInterfaces();
for (int i=0; i<clazzIfaces.length; i++)
allIfaces.push(clazzIfaces[i]);
c = c.getSuperclass();
}
for (int i=0; i<t1.ifaces.length; i++)
}
for (int i=0; i<t1.ifaces.length; i++)
allIfaces.push(t1.ifaces[i]);
/* Now consider each interface. If any clazz or interface
* in t2 implements it, add it to the ifaces vector.
* Otherwise consider all sub interfaces.
*/
iface_loop:
while (!allIfaces.isEmpty()) {
ClassDeclaration iface = (ClassDeclaration) allIfaces.pop();
ClassDefinition idef = iface.getClassDefinition(env);
if (clazz != null && idef.implementedBy(env, clazz))
/* We can skip this, as clazz does already imply it.
*/
continue iface_loop;
iface_loop:
while (!allIfaces.isEmpty()) {
Class iface = (Class) allIfaces.pop();
if (clazz != null && implementedBy(iface, clazz))
/* We can skip this, as clazz does already imply it.
*/
continue iface_loop;
if (t2.clazz != null && idef.implementedBy(env, t2.clazz)) {
if (t2.clazz != null && implementedBy(iface, t2.clazz)) {
ifaces.addElement(iface);
continue iface_loop;
}
for (int i=0; i<t2.ifaces.length; i++) {
if (implementedBy(iface, t2.ifaces[i])) {
ifaces.addElement(iface);
continue iface_loop;
}
for (int i=0; i<t2.ifaces.length; i++) {
if (idef.implementedBy(env, t2.ifaces[i])) {
ifaces.addElement(iface);
continue iface_loop;
}
}
/* This interface is not implemented by any of the other
* ifaces. Try its parent interfaces now.
*/
ClassDeclaration clazzIfaces[] = idef.getInterfaces();
for (int i=0; i<clazzIfaces.length; i++)
allIfaces.push(clazzIfaces[i]);
}
} catch (ClassNotFound ex) {
return tError;
}
ClassDeclaration[] ifaceArray = new ClassDeclaration[ifaces.size()];
/* This interface is not implemented by any of the other
* ifaces. Try its parent interfaces now.
*/
Class clazzIfaces[] = iface.getInterfaces();
for (int i=0; i<clazzIfaces.length; i++)
allIfaces.push(clazzIfaces[i]);
}
Class[] ifaceArray = new Class[ifaces.size()];
ifaces.copyInto(ifaceArray);
return new ClassInterfacesType(clazz, ifaceArray);
}
@ -329,12 +327,11 @@ public class ClassInterfacesType extends MyType {
return sb.append("}").append(string).toString();
} else {
if (clazz != null)
return clazz.getType().typeString(string, flag1, flag2);
return clazz.toString() + string;
else if (ifaces.length > 0)
return ifaces[0].getType().typeString(string, flag1, flag2);
return ifaces[0].toString() + string;
else
return tError.typeString(string,flag1,flag2);
return tError.toString() + string;
}
}
}

Loading…
Cancel
Save