我正在搜索 Perl 等效的python' re.sub
,其中根据文档 repl可以是字符串或可调用
我最终发现了perl e
函数的s//
修饰符,它允许我执行以下操作:
my $n = 1;
sub repl {
return $_[0] x $n ++;
}
my $hw = "hello world";
$hw =~ s/(l)/repl $1/eg;
say $hw;
获取helllo worllld
。
我发现在安全方面有点怀疑。我假设 Mallory 控制了$hw
字符串,并且我不相信这种方法的安全性,尽管我无法找到任何可能的利用。
确定/ee
修饰符存在固有错误:搜索单词" vendetta"在this thread中获取线索。双 - e
让我认为评估的表达式(在本例中为repl $1
)对应于隐式eval('repl $1')
。
是这样的吗?
$hw = "foo lish"
; /(f.*h)/
(与整个foo lish
匹配); 我们显然已调用repl("foo lish")
,但您可能想知道是否要评估repl foo lish
。这有点模棱两可。这不是一个问题,但我的问题是关于可能存在类似模式的陷阱。
答案 0 :(得分:3)
它不会导致任何数据成为代码。它只是告诉Perl将.pl文件的一部分视为Perl代码。因此,它不会引入任何安全问题。
如果替换运算符是函数,那么
s/pat/repl/ ⇒ substitute($_, qr/pat/, sub { qq/repl/ })
s/pat/repl()/e ⇒ substitute($_, qr/pat/, sub { repl() })
这显然很好。
进一步证明,/e
可以轻松完成所有事情。
s/pat/repl()/e
类似于
s/pat/${\( repl() )/
/ee
可能是一个安全问题。数据可以成为代码。
s/pat/repl/ee
类似于
s/pat/eval "repl"/e
问题在于替换模式插入 [1] 。
$ echo 'print "0wn3d\n";' | perl -e'$_ = <>; s/(.*)/$1/ee'
0wn3d
我从不使用/ee
,因为它掩盖了您使用eval EXPR
的事实。
/ee
。