Rationale of indirect eval and its subtle features

Dmitry A. Soshnikov dmitry.soshnikov at gmail.com
Fri Feb 18 04:52:08 PST 2011


Have no idea what with mail sever again, there is no this message there 
(links in message?). The original question is below:

On 18.02.2011 11:51, Dmitry A. Soshnikov wrote:
> Hello,
>
> As is known, indirect `eval` evaluates in the global context (this 
> note is not for the TC-39 group of course, but for all other who read 
> this list). But what is the big rationale of that indirect eval is 
> allowed to create a global binding even _regardless_ the fact that the 
> global code is _strict_?
>
> I.e.:
>
> "use strict";
>
> eval("var x = 10;"); // direct
> this.eval("var y = 20;"); // indirect
>
> console.log(typeof x, typeof y); // "undefined", "number"
>
> The only _practical_ rationale of the indirect `eval` regarding the 
> strict mode is that via its call it's possible to get the global 
> object via `this` value from any place (since just returning `this` 
> won't work as it's set to `undefined` in a simple function call):
>
> var global = (function () { return this; })(); // ES3, non-strict ES5 way
>
> var global = ("indirect", eval)("this"); // strict ES5
>
> Which else practical/theoretical/academical rationales of the indirect 
> eval are? And what again the rationale that it's allowed to create the 
> global binding (i.e. not in the "sandbox" environment, but reusing 
> `VariableEnvironment` of the "caller" -- not a direct caller though, 
> but the adjusted -- the global scope)? Could you clarify this, I want 
> to give a more concrete explanations for my readers.
>
> P.S.:
>
> Just recently Allen brought a good addition (well, a reminder even 
> better to say, since I also wanted to add it ;) to mention this subtle 
> case with indirect eval and it's ability to affect the global 
> environment regardless the strict mode: 
> http://dmitrysoshnikov.com/ecmascript/es5-chapter-2-strict-mode/#comment-5831
>
> It's without doubts a very needed addition and as is said -- a subtle 
> case, but still -- what are the exact rationales for that? I mentioned 
> this case in Allen's blog before, and though that this is a bug of the 
> spec -- http://www.wirfs-brock.com/allen/posts/39#comment-46
>
> Allen answered that this is related with complexity of implementation, 
> here:
>
> "An /indirect/ eval called from strict code is strict only if the eval 
> code explicit contains an "use strict;" directive. It does not 
> "inherit" the strictness of its caller.
>
> Every call is potentially an indirect eval call. If the strictness of 
> indirect evals depended upon the strictness of the caller then we 
> would have to pass the strictness of the caller through every call. 
> That would require either an extra implicit parameter on every call or 
> the ability to a callee to examine the call stack to to determine the 
> strictness of its caller. We don't want to force this on implementations."
>
> The basic idea is seems clear -- we need to pass a flag that the code 
> of an inner function (from which indirect `eval` was called) is 
> strict, but if the _global_ code is strict -- and indirect `eval` 
> always evaluates in the global context, and moreover, if the global 
> code is strict that means _any_ inner function (except those which are 
> created via `Function` constructor and have no own strictness) is 
> automatically also strict:
>
> "use strict";
>
> (function foo() {
>   // this code is also strict
>   ("indirect", eval)("var x = 10;");
> })();
>
> console.log(x); // 10
>
> is it also required to pass special flags to handle this case?
>
> Thanks,
> Dmitry.

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20110218/2ef816ad/attachment.html>


More information about the es-discuss mailing list