这段代码如何在 SQL 注入中易受攻击?

Posted

技术标签:

【中文标题】这段代码如何在 SQL 注入中易受攻击?【英文标题】:How this piece of code can be vulnerable in SQL-Injection? 【发布时间】:2020-10-15 14:23:31 【问题描述】:

我正在审核以下代码:

function getNormalizedLocationPath($path)

  $path = is_scalar($path) ? strtolower(trim($path)) : '';
  $path = preg_replace('/[^a-z0-9.]/', '', $path);

  return $path;


$path=getNormalizedLocationPath($_GET['path']);
$sql= "INSERT INTO paths VALUES ($path)";

$pdo = new PDO();
$pdo->query($sql);

如您所见,这是一段明显的 SQL 注入漏洞代码,但我很难证明这一点。我如何证明这段代码容易受到我的主管的攻击?

【问题讨论】:

由于“消毒”功能只留下字符 a-z、0-9 和点,我看不出这里会造成多大的损害。超出预期的“扩展” SQL 语法,通常需要在某处使用引号、大括号或至少是空格……由于没有使用引号围绕该值,因此该查询当然只能工作对于以数字开头的值,其他任何内容(除了值关键字,例如null mabye)都会导致开头出现语法错误。 【参考方案1】:

老实说,这段代码可能是安全的。

我没有考虑太多,考虑哪些边缘情况会使其不安全。就像您使用的是旧版本的 php,其中 preg_replace() 不理解 unicode 序列或其他东西。这可能允许某人绕过正则表达式过滤器以 unicode 编码引号字符。我不知道。

不值得深思熟虑的原因是,还有另一种解决方案,代码更简单,而且肯定是安全的:

$sql= "INSERT INTO paths VALUES (?)";

$pdo = new PDO();
$stmt = $pdo->prepare($sql);
$stmt->execute( [ $_GET['path'] ] );

通过使用这样的查询参数,$path 的值将与查询分开,直到它准备好。因此,该值无法引入错误的引号字符或任何其他可能影响 SQL 语句语法的内容。

因此,您根本不需要清理功能。*您可以删除一些代码,这总是使项目更易于维护。

您甚至不必问这个问题,寻求专家帮助来确定消毒是否完全安全。


* 至少不是为了防止 SQL 注入。您可能需要为了应用程序特性而更改该值,但无论您对该值应用什么更改,如果您使用查询参数,您将不必担心 SQL 注入漏洞。

【讨论】:

以上是关于这段代码如何在 SQL 注入中易受攻击?的主要内容,如果未能解决你的问题,请参考以下文章

网站如何防止sql注入攻击的解决办法

SQL注入易受攻击?

如何防止代码注入攻击在PHP

如何防止网站不被SQL注入攻击

如何使我的登录页面易受 SQL 注入攻击?

如何防止sql注入攻击?