Search in sources :

Example 1 with ArrayTypes

use of soot.jimple.toolkits.callgraph.ConstantArrayAnalysis.ArrayTypes in project soot by Sable.

the class OnFlyCallGraphBuilder method addInvokeCallSite.

/*
	 * How type based reflection resolution works:
	 *
	 * In general, for each call to invoke(), we record the local of the receiver
	 * argument and the argument array. Whenever a new type is added to the points
	 * to set of the receiver argument we add that type to the reachingBaseTypes and
	 * try to resolve the reflective method call (see addType, addBaseType, and
	 * updatedNode() in OnFlyCallGraph).
	 *
	 * For added precision, we also record the second argument to invoke. If it is
	 * always null, this means the invoke() call resolves only to nullary methods.
	 *
	 * When the second argument is a variable that must not be null we can narrow
	 * down the called method based on the possible sizes of the argument array and
	 * the types it contains. Whenever a new allocation reaches this variable we
	 * record the possible size of the array (by looking at the allocation site) and
	 * the possible types stored in the array (see updatedNode in OnFlyCallGraph in
	 * the branch wantInvokeArg()). If the size of the array isn't statically known,
	 * the analysis considers methods of all possible arities. In addition, we track
	 * the PAG node corresponding to the array contents. If a new type reaches this
	 * node, we update the possible argument types. (see propagate() in PropWorklist
	 * and the visitor, and updatedFieldRef in OnFlyCallGraph).
	 *
	 * For details on the method resolution process, see resolveInvoke()
	 *
	 * Finally, for cases like o.invoke(b, foo, bar, baz); it is very easy to
	 * statically determine precisely which types are in which argument positions.
	 * This is computed using the ConstantArrayAnalysis and are resolved using
	 * resolveStaticTypes().
	 */
private void addInvokeCallSite(Stmt s, SootMethod container, InstanceInvokeExpr d) {
    Local l = (Local) d.getArg(0);
    Value argArray = d.getArg(1);
    InvokeCallSite ics;
    if (argArray instanceof NullConstant) {
        ics = new InvokeCallSite(s, container, d, l);
    } else {
        if (analysisKey != container) {
            ExceptionalUnitGraph graph = new ExceptionalUnitGraph(container.getActiveBody());
            nullnessCache = new NullnessAnalysis(graph);
            arrayCache = new ConstantArrayAnalysis(graph, container.getActiveBody());
            analysisKey = container;
        }
        Local argLocal = (Local) argArray;
        int nullnessCode;
        if (nullnessCache.isAlwaysNonNullBefore(s, argLocal)) {
            nullnessCode = InvokeCallSite.MUST_NOT_BE_NULL;
        } else if (nullnessCache.isAlwaysNullBefore(s, argLocal)) {
            nullnessCode = InvokeCallSite.MUST_BE_NULL;
        } else {
            nullnessCode = InvokeCallSite.MAY_BE_NULL;
        }
        if (nullnessCode != InvokeCallSite.MUST_BE_NULL && arrayCache.isConstantBefore(s, argLocal)) {
            ArrayTypes reachingArgTypes = arrayCache.getArrayTypesBefore(s, argLocal);
            if (nullnessCode == InvokeCallSite.MAY_BE_NULL) {
                reachingArgTypes.possibleSizes.add(0);
            }
            ics = new InvokeCallSite(s, container, d, l, reachingArgTypes, nullnessCode);
        } else {
            ics = new InvokeCallSite(s, container, d, l, argLocal, nullnessCode);
            invokeArgsToInvokeSite.put(argLocal, ics);
        }
    }
    baseToInvokeSite.put(l, ics);
}
Also used : ExceptionalUnitGraph(soot.toolkits.graph.ExceptionalUnitGraph) ArrayTypes(soot.jimple.toolkits.callgraph.ConstantArrayAnalysis.ArrayTypes) Value(soot.Value) Local(soot.Local) NullConstant(soot.jimple.NullConstant) NullnessAnalysis(soot.jimple.toolkits.annotation.nullcheck.NullnessAnalysis)

Example 2 with ArrayTypes

use of soot.jimple.toolkits.callgraph.ConstantArrayAnalysis.ArrayTypes in project soot by Sable.

the class OnFlyCallGraphBuilder method resolveStaticTypes.

/* End of public methods. */
private void resolveStaticTypes(Set<Type> s, InvokeCallSite ics) {
    ArrayTypes at = ics.reachingTypes();
    for (Type bType : s) {
        SootClass baseClass = ((RefType) bType).getSootClass();
        Iterator<SootMethod> mIt = getPublicMethodIterator(baseClass, at);
        while (mIt.hasNext()) {
            SootMethod sm = mIt.next();
            cm.addVirtualEdge(ics.container(), ics.stmt(), sm, Kind.REFL_INVOKE, null);
        }
    }
}
Also used : RefType(soot.RefType) RefType(soot.RefType) ShortType(soot.ShortType) BooleanType(soot.BooleanType) ByteType(soot.ByteType) Type(soot.Type) DoubleType(soot.DoubleType) FloatType(soot.FloatType) IntType(soot.IntType) CharType(soot.CharType) LongType(soot.LongType) NullType(soot.NullType) RefLikeType(soot.RefLikeType) ArrayType(soot.ArrayType) PrimType(soot.PrimType) ArrayTypes(soot.jimple.toolkits.callgraph.ConstantArrayAnalysis.ArrayTypes) SootMethod(soot.SootMethod) SootClass(soot.SootClass)

Aggregations

ArrayTypes (soot.jimple.toolkits.callgraph.ConstantArrayAnalysis.ArrayTypes)2 ArrayType (soot.ArrayType)1 BooleanType (soot.BooleanType)1 ByteType (soot.ByteType)1 CharType (soot.CharType)1 DoubleType (soot.DoubleType)1 FloatType (soot.FloatType)1 IntType (soot.IntType)1 Local (soot.Local)1 LongType (soot.LongType)1 NullType (soot.NullType)1 PrimType (soot.PrimType)1 RefLikeType (soot.RefLikeType)1 RefType (soot.RefType)1 ShortType (soot.ShortType)1 SootClass (soot.SootClass)1 SootMethod (soot.SootMethod)1 Type (soot.Type)1 Value (soot.Value)1 NullConstant (soot.jimple.NullConstant)1