【问题标题】:How to sanitize input from open files in Perl如何清理 Perl 中打开文件的输入
【发布时间】:2020-01-31 18:56:45
【问题描述】:

我有一个 Perl 脚本,它可以打开一个文件、处理它并打印一些输出。 输入文件被压缩。

$file 的路径作为参数传递给脚本。

以下是我正在使用的当前解决方案:

open(my $fh, "-|", "$gzcat $file") or die("Cannot open $file$!");

该脚本最近在Checkmarx的安全审计中失败,报错如下:

<script> gets user input for the $fh element. This element’s value then flows through the code without being properly sanitized or validated and is eventually displayed to the user in method <method>. This may enable a CrossSite-Scripting attack.

我尝试使用 perl -f 验证文件是否存在,并使用 $file =~ s/[^A-Za-z0-9_\-\.\/]//g; 删除不需要的字符,但它不满足 Checkmarx。

我想知道在 Perl 中清理包含文件路径的输入的正确方法是什么。

【问题讨论】:

  • 听起来您急需proper shell escaping永远不要在没有适当转义的情况下将用户提供的输入转储到 shell 参数中。
  • @tadman 输入由运行在生成文件名的服务器上的不同应用程序提供。
  • 你仍然不能相信$file 是无害的,或者没有shell 字符。例如$file = "a space.txt" 将不起作用。

标签: perl checkmarx


【解决方案1】:

只要您在支持分叉的操作系统上使用 Perl 5.8 或更高版本,或者在 Windows 上使用 5.22 或更高版本,您就可以在运行命令时使用管道打开的列表形式绕过 shell。这可以避免文件名包含 shell 将解释的元字符的问题,例如 & 和空格。

open(my $fh, "-|", $gzcat, $file) or die("Cannot open $file: $!");

但是,这不是所要求的验证或清理,但重要的是要避免漏洞和不当行为。提到的跨站点脚本可能是由于后面提到的文件名被显示;例如,如果它显示在 HTML 页面中,则必须对其进行 HTML 转义,大多数模板系统都有方法来做到这一点。

【讨论】:

  • 文件名本身没有被打印,只有文件的内容被打印。对文件路径进行 HTML 转义会弄乱路径本身,例如路径中的斜杠会被转换为 %2F
【解决方案2】:

我最终用

删除了不需要的字符

$file =~ s/[^A-Za-z0-9_\-\.\/]//g;

使用Perl -f 检查文件是否存在,并使用打开文件 IO::Uncompress::Gunzip

这通过了 Checkmarx 的审核。

【讨论】:

  • 我在Mastering Perl 的“安全编程技术”一章中对此进行了介绍。您可以污染来自文件句柄的数据,并按照您所做的来消除它。另一种说法是“去除不想要的”是说“保持想要”; Mark Jason Dominus 所说的美国和普鲁士方法之间的区别。
猜你喜欢
  • 2018-02-25
  • 1970-01-01
  • 2016-11-08
  • 1970-01-01
  • 2010-12-02
  • 1970-01-01
  • 2014-04-11
  • 2014-08-12
  • 2011-01-28
相关资源
最近更新 更多