| 1 19 20 package edu.umd.cs.findbugs.ba.type; 21 22 import org.apache.bcel.Constants; 23 import org.apache.bcel.generic.ObjectType; 24 import org.apache.bcel.generic.ReferenceType; 25 import org.apache.bcel.generic.Type; 26 27 import edu.umd.cs.findbugs.ba.DataflowAnalysisException; 28 import edu.umd.cs.findbugs.ba.MissingClassException; 29 import edu.umd.cs.findbugs.ba.RepositoryLookupFailureCallback; 30 31 39 public class StandardTypeMerger implements TypeMerger, Constants, ExtendedTypes { 40 private RepositoryLookupFailureCallback lookupFailureCallback; 41 private ExceptionSetFactory exceptionSetFactory; 42 43 49 public StandardTypeMerger(RepositoryLookupFailureCallback lookupFailureCallback, 50 ExceptionSetFactory exceptionSetFactory) { 51 this.lookupFailureCallback = lookupFailureCallback; 52 this.exceptionSetFactory = exceptionSetFactory; 53 } 54 55 public Type mergeTypes(Type a, Type b) throws DataflowAnalysisException { 56 byte aType = a.getType(), bType = b.getType(); 57 58 if (aType == T_TOP) return b; 60 else if (bType == T_TOP) return a; 62 else if (aType == T_BOTTOM || bType == T_BOTTOM) return BottomType.instance(); 64 else if (isReferenceType(aType) && isReferenceType(bType)) { if (aType == T_NULL) 68 return b; 69 else if (bType == T_NULL) 70 return a; 71 72 ReferenceType aRef = (ReferenceType) a; 73 ReferenceType bRef = (ReferenceType) b; 74 return mergeReferenceTypes(aRef, bRef); 75 } else if (isReferenceType(aType) || isReferenceType(bType)) return BottomType.instance(); 77 else if (aType == bType) return a; 79 else if (isIntegerType(aType) && isIntegerType(bType)) return Type.INT; 81 else return BottomType.instance(); 83 } 84 85 91 protected boolean isReferenceType(byte type) { 92 return type == T_OBJECT || type == T_ARRAY || type == T_NULL || type == T_EXCEPTION; 93 } 94 95 99 protected boolean isObjectType(byte type) { 100 return type == T_OBJECT || type == T_EXCEPTION; 101 } 102 103 109 protected boolean isIntegerType(byte type) { 110 return type == T_INT || type == T_BYTE || type == T_BOOLEAN || type == T_CHAR || type == T_SHORT; 111 } 112 113 private static void updateExceptionSet(ExceptionSet exceptionSet, ObjectType type) { 114 if (type instanceof ExceptionObjectType) 115 exceptionSet.addAll(((ExceptionObjectType) type).getExceptionSet()); 116 else 117 exceptionSet.addExplicit(type); 118 } 119 120 130 protected Type mergeReferenceTypes(ReferenceType aRef, ReferenceType bRef) throws DataflowAnalysisException { 131 try { 137 if (isObjectType(aRef.getType()) && isObjectType(bRef.getType()) && 141 (aRef.getType() == T_EXCEPTION || bRef.getType() == T_EXCEPTION)) { 142 ExceptionSet union = exceptionSetFactory.createExceptionSet(); 143 144 updateExceptionSet(union, (ObjectType) aRef); 145 updateExceptionSet(union, (ObjectType) bRef); 146 147 return ExceptionObjectType.fromExceptionSet(union); 148 } 149 150 return aRef.getFirstCommonSuperclass(bRef); 151 } catch (ClassNotFoundException e) { 152 lookupFailureCallback.reportMissingClass(e); 153 throw new MissingClassException(e); 154 } 155 } 156 157 } 158 159 | Popular Tags |