-
Notifications
You must be signed in to change notification settings - Fork 113
CatchBlocksScopeBleed
(legacy summary: catch blocks don't always introduce a new scope.) (legacy labels: Attack-Vector)
Replace global variables.
EcmaScript 262 says that only the Program and FunctionDeclaration constructor introduce new lexical scopes. EcmaScript 262 section 10.1.4 says
During execution within an execution context, the scope chain of the execution context is affected only by with statements (see 12.10) and catch clauses (see 12.14).
Section 12.10 describes with statements:
The with statement adds a computed object to the front of the scope chain of the current execution context, then executes a statement with this augmented scope chain, then restores the scope chain.
Section 12.14 describes catch clauses
The production Catch : catch (Identifier ) Block is evaluated as follows:
- Let C be the parameter that has been passed to this production.
- Create a new object as if by the expression new Object().
- Create a property in the object Result(2). The property's name is Identifier, value is C.value, and attributes are { DontDelete }.
- Add Result(2) to the front of the scope chain.
- Evaluate Block.
- Remove Result(2) from the front of the scope chain.
- Return Result(5).
Existing interpreters fail to implement the semantics of 12.14. Old versions of firefox allow global assignment this way.
IE introduces it as a variable in the local scope, instead of creating a new scope (see bug 1032).
There is no local variable of the same name as the caught variable already in scope, or there is one, and that variable is referenceable outside scope.
Inconsistent
var a = 0;
(function () {
try {
throw 1;
} catch (a) {
}
})();
alert(a); // alerts 1 on old FF
(function () {
var a = 0;
try {
throw 1;
} catch (a) {
}
alert(a); // alerts 1 on IE 6 and 7 (IE 8 not tested)
})();