You can't "alias" eval
and expect it to behave the same. Simple as that. Why? eval
isn't a function.
What is happening is that when you call eval2
, you are setting the variable "cache" to work with the global variables. Therefore, by setting a variable inside of it, you are setting a global variable. However, upon exiting, the variable "cache" returns back to the function scoped one. That's why the second alert
shows 1 - the global variable is being shadowed by the function level one.
This is noted in Annex E (page 239) of ECMAScript (emphasis mine)
10.4.2: In Edition 5, indirect calls to the eval function use the global environment as both the variable environment and lexical environment for the eval code. In Edition 3, the variable and lexical environments of the caller of an indirect eval was used as the environments for the eval code.
The full definition on "Entering Eval Code" is defined in §10.5.2 (page 58) (emphasis mine)
- If there is no calling context or if the eval code is not being evaluated by a direct call (15.1.2.1.1) to the eval function then,
- Initialise the execution context as if it was a global execution context using the eval code as C as described in 10.4.1.1.
- Else,
- Set the ThisBinding to the same value as the ThisBinding of the calling execution context.
- Set the LexicalEnvironment to the same value as the LexicalEnvironment of the calling execution
context.
- Set the VariableEnvironment to the same value as the VariableEnvironment of the calling execution
context.
- If the eval code is strict code, then
- Let strictVarEnv be the result of calling NewDeclarativeEnvironment passing the LexicalEnvironment as the argument.
- Set the LexicalEnvironment to strictVarEnv.
- Set the VariableEnvironment to strictVarEnv.
- Perform Declaration Binding Instantiation as described in 10.5 using the eval code.