严格模式提供的一个保证是在严格的函数代码中,标识符arguments
总是引用该函数的Arguments对象。
function fn () {
'use strict';
// malicious code
arguments // still refers to the function's Arguments object
}
因此,无论在// malicious code
注入什么代码,arguments
标识符在整个函数调用期间都会不可变地绑定到函数的Arguments对象。
我想知道是否为eval
标识符提供了相同的保证,即带有保证的eval
标识符是否始终引用内置的全局eval
函数?< / p>
我想指出,如果我们的严格代码嵌套在非严格代码中,则上面提到的保证是 not 。允许非严格代码创建本地"eval"
绑定,或者改变全局"eval"
绑定。 (另外,如果另一个非严格程序使用相同的全局对象(如在包含多个脚本的网页中),则也不提供上述保证。)
因此,为了这个问题,我想定义以下场景:
我们的程序由一个严格的IIFE组成,如下所示:
(function () {
'use strict';
// malicious code
eval // does it still refer to the built-in global eval function?
}());
鉴于这些条件,是否可以在\\ malicious code
注入代码,这将改变eval
标识符的值?
答案 0 :(得分:2)
理论上,根据附件C,不应该将eval
标识符重新分配给全局对象的eval
属性以外的其他属性,或者用局部变量对其进行掩码:
标识符eval或参数可能不会显示为赋值运算符(11.13)或PostfixExpression(11.3)的LeftHandSideExpression,也不会显示为由前缀增量(11.4.4)或前缀减量(11.4)操作的UnaryExpression。 5)运营商。
...
如果标识符“eval”或标识符“arguments”作为PropertyAssignment的PropertySetParameterList中的标识符出现,它包含在严格的代码中,或者如果其FunctionBody是严格的代码(11.1.5),那么这是一个SyntaxError。 p>
...
如果标识符eval或参数出现在严格模式FunctionDeclaration或FunctionExpression(13.1)的FormalParameterList中,则为SyntaxError
......等等。
如下所述,可以通过为全局对象的该属性分配新值来更改全局eval函数。可以通过在严格模式下间接调用eval
来获取对全局对象的引用:
var glob = (0,eval)('this');
您可以将其扩展为在非严格模式下可靠运行的东西:
var glob = (function(){ return this || (0,eval)('this') }());
...然后将其eval
属性分配给其他内容。
虽然eval
仍然与全局对象的eval
属性相同,但它不再是内置的eval
,它应符合您的条件。
答案 1 :(得分:0)
不,据我所知,你不能在严格模式下覆盖本机eval函数。下面的代码会给出以下错误。 SyntaxError: Assignment to eval or arguments is not allowed in strict mode
(function () {
'use strict';
eval = function(){ console.log('eval invoked'); }
eval();
}());