Skip to content

Commit

Permalink
feat(spgroup#31): add support to DefaultConstructor
Browse files Browse the repository at this point in the history
  • Loading branch information
barbosamaatheus committed Nov 18, 2021
1 parent a50793b commit bff8820
Show file tree
Hide file tree
Showing 3 changed files with 80 additions and 34 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
import soot.jimple.InvokeStmt;
import soot.jimple.StaticFieldRef;

import java.util.*;
import java.util.Objects;

/**
* Information wee keep while traversing
Expand Down Expand Up @@ -99,4 +99,9 @@ public boolean equals(Object o) {
public int hashCode() {
return Objects.hash(local, stmt);
}

@Override
public String toString() {
return "DataFlowAbstraction{ " + stmt + "}";
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,13 @@
import br.unb.cic.exceptions.ValueNotHandledException;
import soot.*;
import soot.jimple.*;
import soot.jimple.internal.JAssignStmt;
import soot.jimple.internal.JimpleLocal;
import soot.jimple.toolkits.callgraph.CallGraph;
import soot.jimple.toolkits.callgraph.Edge;
import soot.toolkits.scalar.ArraySparseSet;
import soot.toolkits.scalar.FlowSet;
import soot.util.Chain;

import java.util.*;
import java.util.logging.Level;
Expand Down Expand Up @@ -59,28 +62,16 @@ public Set<Conflict> getConflicts() {

@Override
protected void internalTransform(String s, Map<String, String> map) {
long tempoInicial = System.currentTimeMillis();
long startTime = System.currentTimeMillis();

List<SootMethod> methods = Scene.v().getEntryPoints();
methods.forEach(sootMethod -> traverse(new ArraySparseSet<>(), sootMethod, Statement.Type.IN_BETWEEN));

Set<Conflict> conflictsFilter = filterConflicts(getConflicts());
conflictsFilter.forEach(conflict -> logger.log(Level.INFO, conflict.toStringAbstract()));

logger.log(Level.INFO, () -> String.format("%s", "CONFLICTS: " + conflictsFilter));

long tempoFinal = System.currentTimeMillis();
System.out.println("Tempo de execução de: " + ((tempoFinal - tempoInicial) / 1000d) + "s");

/* left.forEach(dataFlowAbstraction -> {
String leftStmt = String.format("%s", "LEFT: " + dataFlowAbstraction.getStmt());
logger.log(Level.INFO, leftStmt);
});
right.forEach(dataFlowAbstraction -> {
String rightStmt = String.format("%s", "RIGHT: " + dataFlowAbstraction.getStmt());
logger.log(Level.INFO, rightStmt);
}); */
long finalTime = System.currentTimeMillis();
System.out.println("Runtime: " + ((finalTime - startTime) / 1000d) + "s");
}

public void configureEntryPoints() {
Expand Down Expand Up @@ -121,9 +112,13 @@ private Set<Conflict> filterConflicts(Set<Conflict> conflictsResults) {
}
for (Conflict conflict : conflictsResults) {
for (Conflict filter : conflictsFilter) {
if ((!conflict.getSourceTraversedLine().get(0).equals(filter.getSourceTraversedLine().get(0))) && (!conflict.getSinkTraversedLine().get(0).equals(filter.getSinkTraversedLine().get(0)))) {
conflictsFilter.add(conflict);
if (!conflict.getSourceTraversedLine().isEmpty() && !conflict.getSinkTraversedLine().isEmpty()) {
if ((!conflict.getSourceTraversedLine().get(0).equals(filter.getSourceTraversedLine().get(0)))
&& (!conflict.getSinkTraversedLine().get(0).equals(filter.getSinkTraversedLine().get(0)))) {
conflictsFilter.add(conflict);
}
}

}
}
return conflictsFilter;
Expand All @@ -141,7 +136,7 @@ private Set<Conflict> filterConflicts(Set<Conflict> conflictsResults) {
private FlowSet<DataFlowAbstraction> traverse(FlowSet<DataFlowAbstraction> in, SootMethod sootMethod,
Statement.Type flowChangeTag) {

if (this.traversedMethods.contains(sootMethod) || this.traversedMethods.size() > 10 || sootMethod.isPhantom()) {
if (this.traversedMethods.contains(sootMethod) || this.traversedMethods.size() > 2 || sootMethod.isPhantom()) {
return in;
}

Expand All @@ -151,6 +146,7 @@ private FlowSet<DataFlowAbstraction> traverse(FlowSet<DataFlowAbstraction> in, S
Body body = definition.retrieveActiveBodySafely(sootMethod);

if (body != null) {
handleConstructor(in, sootMethod, flowChangeTag);
for (Unit unit : body.getUnits()) {
TraversedLine traversedLine = new TraversedLine(sootMethod, unit.getJavaSourceStartLineNumber());

Expand All @@ -169,6 +165,42 @@ private FlowSet<DataFlowAbstraction> traverse(FlowSet<DataFlowAbstraction> in, S
return in;
}

private void handleConstructor(FlowSet<DataFlowAbstraction> in, SootMethod sootMethod,
Statement.Type flowChangeTag) {
if (sootMethod.isConstructor()) {
Chain<SootField> sootFieldsInClass = sootMethod.getDeclaringClass().getFields();

sootFieldsInClass.forEach(sootField -> {
trasformFieldsIntoStatements(in, sootMethod, flowChangeTag, sootField);
});
}
}

private void trasformFieldsIntoStatements(FlowSet<DataFlowAbstraction> in, SootMethod sootMethod, Statement.Type flowChangeTag, SootField sootField) {
String declaringClassShortName = sootField.getDeclaringClass().getShortName();
String formatName =
declaringClassShortName.substring(0, 1).toLowerCase() + declaringClassShortName.substring(1);

JimpleLocal base = new JimpleLocal(formatName, RefType.v(sootField.getDeclaringClass()));
SootFieldRef fieldRef = Scene.v().makeFieldRef(sootField.getDeclaringClass(),
sootField.getName(), sootField.getType(), sootField.isStatic());

Value value = getValue(base, fieldRef);
Unit unit = new JAssignStmt(value, NullConstant.v());
createAndAddStmt(in, sootMethod, flowChangeTag, unit);

}

private Value getValue(JimpleLocal base, SootFieldRef fieldRef) {
Value value;
if (fieldRef.isStatic()) {
value = Jimple.v().newStaticFieldRef(fieldRef);
} else {
value = Jimple.v().newInstanceFieldRef(base, fieldRef);
}
return value;
}

private FlowSet<DataFlowAbstraction> runAnalysisWithTaggedUnit(FlowSet<DataFlowAbstraction> in, SootMethod sootMethod,
Statement.Type flowChangeTag, Unit unit) {
return runAnalysis(in, sootMethod, flowChangeTag, unit, true);
Expand Down Expand Up @@ -207,10 +239,7 @@ private FlowSet<DataFlowAbstraction> runAnalysis(FlowSet<DataFlowAbstraction> in

separeteAbstraction(in);
if (tagged) {
Statement stmt = getStatementAssociatedWithUnit(sootMethod, unit, flowChangeTag);
stmt.setTraversedLine(new ArrayList<>(this.stacktraceList));
// logger.log(Level.INFO, () -> String.format("%s", "stmt: " + stmt.toString()));
gen(in, stmt);
createAndAddStmt(in, sootMethod, flowChangeTag, unit);
} else {
kill(in, unit);
}
Expand Down Expand Up @@ -239,6 +268,12 @@ In this case, this condition will be executed for the call to the foo() method a
return in;
}

private void createAndAddStmt(FlowSet<DataFlowAbstraction> in, SootMethod sootMethod, Statement.Type flowChangeTag, Unit unit) {
Statement stmt = getStatementAssociatedWithUnit(sootMethod, unit, flowChangeTag);
stmt.setTraversedLine(new ArrayList<>(this.stacktraceList));
gen(in, stmt);
}

private void separeteAbstraction(FlowSet<DataFlowAbstraction> in) {
in.forEach(item -> {
if (item.getStmt().isLefAndRightStatement()) {
Expand Down Expand Up @@ -269,11 +304,16 @@ private FlowSet<DataFlowAbstraction> executeCallGraph(FlowSet<DataFlowAbstractio
flowSetList.add(traverseResult);
}


FlowSet<DataFlowAbstraction> flowSetUnion = new ArraySparseSet<>();
for (FlowSet<DataFlowAbstraction> flowSet : flowSetList) {
flowSetUnion.union(flowSet);
}

if (flowSetUnion.isEmpty()) {
return in;
}

return flowSetUnion;
}

Expand Down Expand Up @@ -348,11 +388,6 @@ private void removeAll(ValueBox valueBox, FlowSet<DataFlowAbstraction> rightOrLe
rightOrLeftList.forEach(dataFlowAbstraction -> {
try {
if (containsValue(dataFlowAbstraction, valueBox.getValue())) {
rightOrLeftList.forEach(dt -> {
if (dt.getStmt().getSourceCodeLineNumber().equals(dataFlowAbstraction.getStmt().getSourceCodeLineNumber())) {
rightOrLeftList.remove(dt);
}
});
rightOrLeftList.remove(dataFlowAbstraction);
}
} catch (ValueNotHandledException e) {
Expand All @@ -363,7 +398,7 @@ private void removeAll(ValueBox valueBox, FlowSet<DataFlowAbstraction> rightOrLe

private boolean containsValue(DataFlowAbstraction dataFlowAbstraction, Value value) throws ValueNotHandledException {
if (dataFlowAbstraction.getValue() instanceof InstanceFieldRef && value instanceof InstanceFieldRef) {
return ((InstanceFieldRef) dataFlowAbstraction.getValue()).getFieldRef().equals(((InstanceFieldRef) value).getFieldRef());
return ((InstanceFieldRef) dataFlowAbstraction.getValue()).getFieldRef().getSignature().equals(((InstanceFieldRef) value).getFieldRef().getSignature());
}
if (dataFlowAbstraction.getValue() instanceof Local && value instanceof Local) {
return dataFlowAbstraction.getValue().equals(value);
Expand All @@ -372,7 +407,7 @@ private boolean containsValue(DataFlowAbstraction dataFlowAbstraction, Value val
return dataFlowAbstraction.getValue().equals(value);
}
if (dataFlowAbstraction.getValue() instanceof StaticFieldRef && value instanceof StaticFieldRef) {
return ((StaticFieldRef) dataFlowAbstraction.getValue()).getField().getName().equals(((StaticFieldRef) value).getField().getName());
return ((StaticFieldRef) dataFlowAbstraction.getValue()).getFieldRef().getSignature().equals(((StaticFieldRef) value).getFieldRef().getSignature());
}
if (!dataFlowAbstraction.getValue().getClass().equals(value.getClass())) {
return false;
Expand Down
14 changes: 10 additions & 4 deletions src/main/java/br/unb/cic/analysis/model/Conflict.java
Original file line number Diff line number Diff line change
Expand Up @@ -110,11 +110,17 @@ public int hashCode() {


public String toStringAbstract() {
return String.format("source(%s, %s, %d, %s, %s) => sink(%s, %s, %d, %s, %s)", sourceTraversedLine.get(0).getSootClass(),
sourceTraversedLine.get(0).getSootMethod(), sourceTraversedLine.get(0).getLineNumber(), sourceUnit,
if (!sourceTraversedLine.isEmpty() && !sinkTraversedLine.isEmpty()) {
return String.format("source(%s, %s, %d, %s, %s) => sink(%s, %s, %d, %s, %s)", sourceTraversedLine.get(0).getSootClass(),
sourceTraversedLine.get(0).getSootMethod(), sourceTraversedLine.get(0).getLineNumber(), sourceUnit,
sourceTraversedLine,
sinkTraversedLine.get(0).getSootClass(), sinkTraversedLine.get(0).getSootMethod(),
sinkTraversedLine.get(0).getLineNumber(), sinkUnit, sinkTraversedLine);
}
return String.format("source(%s, %s) => sink(%s, %s)", sourceUnit,
sourceTraversedLine,
sinkTraversedLine.get(0).getSootClass(), sinkTraversedLine.get(0).getSootMethod(),
sinkTraversedLine.get(0).getLineNumber(), sinkUnit, sinkTraversedLine);
sinkUnit, sinkTraversedLine);

}


Expand Down

0 comments on commit bff8820

Please sign in to comment.