From 667dcc2e49e241fdff00368bfcfffc987bf62e9d Mon Sep 17 00:00:00 2001 From: Matt Brown Date: Tue, 29 Jun 2021 17:05:39 -0400 Subject: [PATCH] No false-positives for tainting through array keys --- src/Psalm/Internal/Codebase/DataFlowGraph.php | 4 +++- tests/TaintTest.php | 20 ++++++++++++++----- 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/src/Psalm/Internal/Codebase/DataFlowGraph.php b/src/Psalm/Internal/Codebase/DataFlowGraph.php index f2765645c..5d4f9547a 100644 --- a/src/Psalm/Internal/Codebase/DataFlowGraph.php +++ b/src/Psalm/Internal/Codebase/DataFlowGraph.php @@ -63,7 +63,9 @@ abstract class DataFlowGraph ) : bool { $el = strlen($expression_type); - if (substr($path_type, 0, $el + 7) === $expression_type . '-fetch-') { + // arraykey-fetch requires a matching arraykey-assignment at the same level + // otherwise the tainting is not valid + if (substr($path_type, 0, $el + 7) === $expression_type . '-fetch-' || $path_type === 'arraykey-fetch') { $fetch_nesting = 0; $previous_path_types = array_reverse($previous_path_types); diff --git a/tests/TaintTest.php b/tests/TaintTest.php index 20e7e4154..80925b52f 100644 --- a/tests/TaintTest.php +++ b/tests/TaintTest.php @@ -630,6 +630,16 @@ class TaintTest extends TestCase echo U::foo($_GET["foo"], true); echo U::foo($_GET["foo"]);' ], + 'keysAreNotTainted' => [ + ' $_) { + echo $key; + } + } + + takesArray(["good" => $_GET["bad"]]);' + ], ]; } @@ -2128,15 +2138,15 @@ class TaintTest extends TestCase $res = Wdb::query("SELECT blah FROM tablea ORDER BY ". $order. " DESC");', 'error_message' => 'TaintedSql', ], - 'taintArrayKey' => [ + 'keysAreTainted' => [ ' $value) { - echo $key . " " . $value; + function takesArray(array $arr): void { + foreach ($arr as $key => $_) { + echo $key; } } - doTheMagic([(string)$_GET["bad"] => "foo"]);', + takesArray([$_GET["bad"] => "good"]);', 'error_message' => 'TaintedHtml', ], 'taintArrayKeyWithExplicitSink' => [