4949import soot .Type ;
5050import soot .Unit ;
5151import soot .Value ;
52+ import soot .ValueBox ;
5253import soot .jimple .AssignStmt ;
5354import soot .jimple .DynamicInvokeExpr ;
5455import soot .jimple .InvokeExpr ;
@@ -643,6 +644,31 @@ private static List<Stmt> patchStringConcatInstruction(Stmt callSite, DynamicInv
643644 || calleeSubSig .equals (scene .getSubSigNumberer ().findOrAdd (SIG_CONCAT ))) {
644645 // We initialize a StringBuilder
645646 Local sb = lg .generateLocal (rtStringBuilder );
647+ Local replace = null , replaceWith = null ;
648+
649+ if (callSite instanceof AssignStmt ) {
650+ AssignStmt assign = (AssignStmt ) callSite ;
651+ Iterator <ValueBox > uses = callSite .getUseBoxesIterator ();
652+ while (uses .hasNext ()) {
653+ Value lop = assign .getLeftOp ();
654+ if (uses .next ().getValue () == lop ) {
655+ //Since FlowDroid doesn't support tracking the taint over this statement, we have a problem:
656+ //e.g.
657+ //tainted = dynamicinvoke "makeConcatWithConstants" <java.lang.String (java.lang.String,java.lang.String)>(tainted, tainted2) ...
658+ //this would erroneously clear the taint on tainted
659+ //to avoid that, we introduce an alias before that statement and use that instead for our concatenation.
660+ Local alias = lg .generateLocal (lop .getType ());
661+ Body body = callSite .getContainingBody ();
662+ AssignStmt assignAlias = Jimple .v ().newAssignStmt (alias , lop );
663+ assignAlias .addTag (SimulatedCodeElementTag .TAG );
664+ assignAlias .addTag (SimulatedDynamicInvokeTag .TAG );
665+ body .getUnits ().insertBefore (assignAlias , callSite );
666+ replace = (Local ) lop ;
667+ replaceWith = alias ;
668+ break ;
669+ }
670+ }
671+ }
646672
647673 Stmt stmt = jimple .newAssignStmt (sb , jimple .newNewExpr (rtStringBuilder ));
648674 stmt .addTag (SimulatedCodeElementTag .TAG );
@@ -659,6 +685,9 @@ private static List<Stmt> patchStringConcatInstruction(Stmt callSite, DynamicInv
659685 for (int i = 0 ; i < diexpr .getArgCount (); i ++) {
660686 // Call toString() on the argument
661687 Value arg = diexpr .getArg (i );
688+ if (arg == replace ) {
689+ arg = replaceWith ;
690+ }
662691 Type argType = arg .getType ();
663692 SootMethodRef appendRef ;
664693 if (argType instanceof RefType )
0 commit comments