|
61 | 61 | import soot.jimple.infoflow.methodSummary.data.sourceSink.AbstractFlowSinkSource; |
62 | 62 | import soot.jimple.infoflow.methodSummary.data.sourceSink.ConstraintType; |
63 | 63 | import soot.jimple.infoflow.methodSummary.data.sourceSink.FlowConstraint; |
| 64 | +import soot.jimple.infoflow.methodSummary.data.sourceSink.FlowSink; |
64 | 65 | import soot.jimple.infoflow.methodSummary.data.sourceSink.FlowSource; |
65 | 66 | import soot.jimple.infoflow.methodSummary.data.summary.AbstractMethodSummary; |
66 | 67 | import soot.jimple.infoflow.methodSummary.data.summary.ClassMethodSummaries; |
@@ -143,43 +144,69 @@ public void handleFollowReturnsPastSeeds(Abstraction d1, Unit u, Abstraction d2) |
143 | 144 | protected void handleFlowSourceInGap(Unit u, Abstraction d2) { |
144 | 145 | final boolean reverseFlows = manager.getConfig() |
145 | 146 | .getDataFlowDirection() == InfoflowConfiguration.DataFlowDirection.Backwards; |
146 | | - if (u instanceof ReturnStmt) { |
147 | | - ReturnStmt retStmt = (ReturnStmt) u; |
148 | | - if (retStmt.getOp() == d2.getAccessPath().getPlainValue()) { |
149 | | - SootMethod sm = manager.getICFG().getMethodOf(u); |
150 | | - for (Unit callSite : manager.getICFG().getCallersOf(sm)) { |
151 | | - Stmt sCallSite = (Stmt) callSite; |
152 | | - ClassSummaries summaries = getFlowSummariesForMethod(sCallSite, |
153 | | - sCallSite.getInvokeExpr().getMethod(), null); |
154 | | - for (MethodFlow flow : summaries.getAllFlows()) { |
155 | | - FlowSource src = flow.source(); |
156 | | - if (src.hasGap() && src.isReturn() && isImplementationOf(sm, src.getGap().getSignature())) { |
157 | | - // We have a flow from the return value of the gap to somewhere |
158 | | - |
159 | | - // Create taints from the abstractions |
160 | | - Set<Taint> returnTaints = createTaintFromAccessPathOnReturn(d2.getAccessPath(), |
161 | | - (Stmt) u, src.getGap()); |
162 | | - if (returnTaints == null) |
163 | | - continue; |
164 | | - |
165 | | - // Create the new propagator, one for every taint |
166 | | - for (Taint returnTaint : returnTaints) { |
167 | | - AccessPathPropagator propagator = new AccessPathPropagator(returnTaint); |
168 | | - AccessPathPropagator newPropagator = applyFlow(flow, propagator); |
169 | | - if (newPropagator != null) { |
170 | | - AccessPath ap = createAccessPathFromTaint(newPropagator.getTaint(), sCallSite, |
171 | | - reverseFlows); |
172 | | - if (ap != null) { |
173 | | - Abstraction zeroValue = manager.getMainSolver().getTabulationProblem() |
174 | | - .zeroValue(); |
175 | | - Abstraction abs = d2.deriveNewAbstraction(ap, sCallSite); |
176 | | - for (Unit succUnit : manager.getICFG().getSuccsOf(callSite)) |
177 | | - manager.getMainSolver().processEdge( |
178 | | - new PathEdge<Unit, Abstraction>(zeroValue, succUnit, abs)); |
179 | | - } |
180 | | - } |
181 | | - } |
182 | 147 |
|
| 148 | + // We can only handle an FRPS case if the taint actually leaves the method |
| 149 | + boolean taintLeavesMethod = false; |
| 150 | + SootMethod callee = manager.getICFG().getMethodOf(u); |
| 151 | + if (reverseFlows) { |
| 152 | + taintLeavesMethod = callee.getActiveBody().getParameterLocals() |
| 153 | + .contains(d2.getAccessPath().getPlainValue()); |
| 154 | + } else { |
| 155 | + if (u instanceof ReturnStmt) { |
| 156 | + ReturnStmt retStmt = (ReturnStmt) u; |
| 157 | + taintLeavesMethod = retStmt.getOp() == d2.getAccessPath().getPlainValue(); |
| 158 | + } |
| 159 | + } |
| 160 | + if (!taintLeavesMethod) |
| 161 | + return; |
| 162 | + |
| 163 | + for (Unit callSite : manager.getICFG().getCallersOf(callee)) { |
| 164 | + Stmt sCallSite = (Stmt) callSite; |
| 165 | + ClassSummaries summaries = getFlowSummariesForMethod(sCallSite, sCallSite.getInvokeExpr().getMethod(), |
| 166 | + null); |
| 167 | + for (MethodFlow flow : summaries.getAllFlows()) { |
| 168 | + FlowSource src = flow.source(); |
| 169 | + FlowSink tgt = flow.sink(); |
| 170 | + |
| 171 | + boolean flowMatchesTaint = false; |
| 172 | + if (!reverseFlows && src.isReturn() && src.hasGap() |
| 173 | + && isImplementationOf(callee, src.getGap().getSignature())) { |
| 174 | + // We have a flow from the return value of the gap to somewhere |
| 175 | + flowMatchesTaint = true; |
| 176 | + } else if (reverseFlows && tgt.isParameter() && tgt.hasGap() |
| 177 | + && isImplementationOf(callee, tgt.getGap().getSignature())) { |
| 178 | + // We have a backward flow to a parameter |
| 179 | + flowMatchesTaint = true; |
| 180 | + } |
| 181 | + if (!flowMatchesTaint) |
| 182 | + continue; |
| 183 | + |
| 184 | + // Create the taint from the incoming access path |
| 185 | + Set<Taint> returnTaints = createTaintFromAccessPathOnReturn(d2.getAccessPath(), (Stmt) u, |
| 186 | + reverseFlows ? tgt.getGap() : src.getGap()); |
| 187 | + if (returnTaints == null) |
| 188 | + continue; |
| 189 | + |
| 190 | + // Create the new propagator, one for every taint |
| 191 | + for (Taint returnTaint : returnTaints) { |
| 192 | + MethodFlow curFlow = flow; |
| 193 | + AccessPathPropagator propagator = new AccessPathPropagator(returnTaint); |
| 194 | + if (reverseFlows) { |
| 195 | + propagator = propagator.deriveInversePropagator(); |
| 196 | + curFlow = flow.reverse(); |
| 197 | + } |
| 198 | + AccessPathPropagator newPropagator = applyFlow(curFlow, propagator); |
| 199 | + if (newPropagator != null) { |
| 200 | + AccessPath ap = createAccessPathFromTaint(newPropagator.getTaint(), sCallSite, |
| 201 | + reverseFlows); |
| 202 | + if (ap != null) { |
| 203 | + Abstraction zeroValue = manager.getMainSolver().getTabulationProblem().zeroValue(); |
| 204 | + Abstraction abs = d2.deriveNewAbstraction(ap, reverseFlows ? sCallSite : (Stmt) u); |
| 205 | + if (reverseFlows) |
| 206 | + abs.setCorrespondingCallSite(sCallSite); |
| 207 | + for (Unit succUnit : manager.getICFG().getSuccsOf(callSite)) |
| 208 | + manager.getMainSolver() |
| 209 | + .processEdge(new PathEdge<Unit, Abstraction>(zeroValue, succUnit, abs)); |
183 | 210 | } |
184 | 211 | } |
185 | 212 | } |
@@ -2148,6 +2175,8 @@ public Set<Abstraction> getInverseTaintsForMethod(Stmt stmt, Abstraction d1, Abs |
2148 | 2175 | if (!stmt.containsInvokeExpr()) |
2149 | 2176 | return Collections.singleton(taintedAbs); |
2150 | 2177 |
|
| 2178 | + SootMethod sm = manager.getICFG().getMethodOf(stmt); |
| 2179 | + |
2151 | 2180 | ByReferenceBoolean classSupported = new ByReferenceBoolean(false); |
2152 | 2181 | // Get the cached data flows |
2153 | 2182 | final SootMethod method = stmt.getInvokeExpr().getMethod(); |
|
0 commit comments