Chromium Code Reviews| Index: src/parser.cc |
| diff --git a/src/parser.cc b/src/parser.cc |
| index f32e9177b5a9120905a287fb1fdac1891c3eb7a6..948c21acc84cef9f04a1c9ef828159de6afa27a5 100644 |
| --- a/src/parser.cc |
| +++ b/src/parser.cc |
| @@ -1210,7 +1210,7 @@ Statement* Parser::ParseStatement(ZoneStringList* labels, bool* ok) { |
| Statement* stmt = NULL; |
| switch (peek()) { |
| case Token::LBRACE: |
| - return ParseBlock(labels, ok); |
| + return ParseScopedBlock(labels, ok); |
| case Token::CONST: // fall through |
| case Token::VAR: |
| @@ -1510,6 +1510,53 @@ Block* Parser::ParseBlock(ZoneStringList* labels, bool* ok) { |
| } |
| +Statement* Parser::ParseScopedBlock(ZoneStringList* labels, bool* ok) { |
| + if (!FLAG_harmony_block_scoping) return ParseBlock(labels, ok); |
|
Kevin Millikin (Chromium)
2011/08/10 11:19:27
This is OK for now, but you should try to think of
Steven
2011/08/10 12:21:00
Yes sure. But indeed I think this should be done w
|
| + |
| + // Construct block expecting 16 statements. |
| + Block* body = new(zone()) Block(isolate(), labels, 16, false); |
| + Scope* saved_scope = top_scope_; |
| + Scope* block_scope = NewScope(top_scope_, |
| + Scope::BLOCK_SCOPE, |
| + inside_with()); |
| + body->set_block_scope(block_scope); |
| + block_scope->DeclareLocal(isolate()->factory()->block_scope_symbol(), |
| + Variable::VAR); |
| + if (top_scope_->is_strict_mode()) { |
| + block_scope->EnableStrictMode(); |
| + } |
| + top_scope_ = block_scope; |
| + |
| + // Parse the statements and collect escaping labels. |
| + TargetCollector collector; |
| + Target target(&this->target_stack_, &collector); |
| + Expect(Token::LBRACE, CHECK_OK); |
| + { |
| + Target target_body(&this->target_stack_, body); |
| + InitializationBlockFinder block_finder(top_scope_, target_stack_); |
| + |
| + while (peek() != Token::RBRACE) { |
| + Statement* stat = ParseStatement(NULL, CHECK_OK); |
| + if (stat && !stat->IsEmpty()) { |
| + body->AddStatement(stat); |
| + block_finder.Update(stat); |
| + } |
| + } |
| + } |
| + Expect(Token::RBRACE, CHECK_OK); |
| + |
| + // Create exit block. |
| + Block* exit = new(zone()) Block(isolate(), NULL, 1, false); |
| + exit->AddStatement(new(zone()) ExitContextStatement()); |
| + |
| + // Return a try-finally statement. |
| + TryFinallyStatement* result = new(zone()) TryFinallyStatement(body, exit); |
| + result->set_escaping_targets(collector.targets()); |
| + top_scope_ = saved_scope; |
| + return result; |
| +} |
| + |
| + |
| Block* Parser::ParseVariableStatement(bool* ok) { |
| // VariableStatement :: |
| // VariableDeclarations ';' |
| @@ -5103,6 +5150,8 @@ bool ParserApi::Parse(CompilationInfo* info) { |
| ASSERT(info->function() == NULL); |
| FunctionLiteral* result = NULL; |
| Handle<Script> script = info->script(); |
| + bool save_block_scoping = FLAG_harmony_block_scoping; |
| + FLAG_harmony_block_scoping = !info->is_native() && FLAG_harmony_block_scoping; |
|
Kevin Millikin (Chromium)
2011/08/10 11:19:27
I'm always nervous about assigning to the flags.
Steven
2011/08/10 12:21:00
Done.
|
| if (info->is_lazy()) { |
| Parser parser(script, true, NULL, NULL); |
| result = parser.ParseLazy(info); |
| @@ -5130,7 +5179,7 @@ bool ParserApi::Parse(CompilationInfo* info) { |
| info->StrictMode()); |
| } |
| } |
| - |
| + FLAG_harmony_block_scoping = save_block_scoping; |
| info->SetFunction(result); |
| return (result != NULL); |
| } |