0

当这个脚本的权限是u=rwx,g=rwx,o=r脚本工作得很好......但是,我需要打开 setuid 位,以便对 smartctl 的调用返回所需的数据而不是错误。

#!/usr/bin/perl

use strict;
use warnings;
use CGI qw(:standard);

my $device = param("device") || "sda";

print header("text/plain");

print "device = $device\n\n";


$ENV{"PATH"} = "/usr/sbin";
open( PS, "smartctl -A /dev/$device |" );
while( <PS> )
{
    print $_ . "\n";
}
close( PS );

当我将权限设置为u=rwxs,g=rwxs,o=r时,脚本在查询未指定时工作device。但是当device指定时,之后什么都不会返回print "device = $device\n\n";

4

1 回答 1

2

您需要查看 Perl 的配置。

perl -MConfig -e 'print "d_suidsafe = $Configu{d_suidsafe}\n"; }'

如果它什么也没说(在 之后没有可见的东西=),那么 Perl 被告知将 SUID 脚本视为不安全的。它以不同于常规脚本的方式对待它们。检查“污点”系统(-T命令行选项);它应该警告下面提到的“脚本注入”问题。


编码建议:

  1. 使用 的三参数形式open
  2. 检查是否open成功。

像这样:

open my $PS, "-|", "smartctl -A /dev/$device"
  or die "Could not popen smartctl: $!";

好吧,可能不是die,但是干净地报告错误并且不要使用未打开的文件句柄。

if (open my $PS, "-|", "smartctl -A /dev/$device")
{
    while (<$PS>)
    {
        print "$_\n";
    }
    close $PS;
}
else
{
    print "Failed to open device: $!";
}

请注意,您需要拒绝或清理以下人员的输入:sda; cp /bin/sh /tmp/...; chmod 6777 /tmp/...在设备参数字段中。这有点像 SQL 注入,只不过这次是“Perl 脚本注入”。它们可能比这更残酷:sda; rm -fr / 2>/dev/null &在清除脚本 setuid 的用户可以修改的文件和目录系统方面做得相当好。在最好的时候,你不能相信用户一英寸。在 setuid 程序中,完全信任用户是一个严重的问题。所有这些都是双倍的(如果不是倍增的话),所以当访问来自网络浏览器时。

于 2012-01-01T22:36:29.630 回答