OLD | NEW |
---|---|
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 393 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
404 return &store_[PreparseDataConstants::kHeaderSize + position]; | 404 return &store_[PreparseDataConstants::kHeaderSize + position]; |
405 } | 405 } |
406 | 406 |
407 | 407 |
408 Scope* Parser::NewScope(Scope* parent, Scope::Type type, bool inside_with) { | 408 Scope* Parser::NewScope(Scope* parent, Scope::Type type, bool inside_with) { |
409 Scope* result = new(zone()) Scope(parent, type); | 409 Scope* result = new(zone()) Scope(parent, type); |
410 result->Initialize(inside_with); | 410 result->Initialize(inside_with); |
411 return result; | 411 return result; |
412 } | 412 } |
413 | 413 |
414 | |
415 Scope* Parser::DeclarationScope() { | |
Kevin Millikin (Chromium)
2011/06/30 09:28:45
As an alternative, we could keep a pair of scopes.
| |
416 Scope* scope = top_scope_; | |
417 while (scope->is_catch_scope()) { | |
418 scope = scope->outer_scope(); | |
419 } | |
420 return scope; | |
421 } | |
422 | |
414 // ---------------------------------------------------------------------------- | 423 // ---------------------------------------------------------------------------- |
415 // Target is a support class to facilitate manipulation of the | 424 // Target is a support class to facilitate manipulation of the |
416 // Parser's target_stack_ (the stack of potential 'break' and | 425 // Parser's target_stack_ (the stack of potential 'break' and |
417 // 'continue' statement targets). Upon construction, a new target is | 426 // 'continue' statement targets). Upon construction, a new target is |
418 // added; it is removed upon destruction. | 427 // added; it is removed upon destruction. |
419 | 428 |
420 class Target BASE_EMBEDDED { | 429 class Target BASE_EMBEDDED { |
421 public: | 430 public: |
422 Target(Target** variable, AstNode* node) | 431 Target(Target** variable, AstNode* node) |
423 : variable_(variable), node_(node), previous_(*variable) { | 432 : variable_(variable), node_(node), previous_(*variable) { |
(...skipping 870 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1294 // is always the function scope. | 1303 // is always the function scope. |
1295 | 1304 |
1296 // If a function scope exists, then we can statically declare this | 1305 // If a function scope exists, then we can statically declare this |
1297 // variable and also set its mode. In any case, a Declaration node | 1306 // variable and also set its mode. In any case, a Declaration node |
1298 // will be added to the scope so that the declaration can be added | 1307 // will be added to the scope so that the declaration can be added |
1299 // to the corresponding activation frame at runtime if necessary. | 1308 // to the corresponding activation frame at runtime if necessary. |
1300 // For instance declarations inside an eval scope need to be added | 1309 // For instance declarations inside an eval scope need to be added |
1301 // to the calling function context. | 1310 // to the calling function context. |
1302 // Similarly, strict mode eval scope does not leak variable declarations to | 1311 // Similarly, strict mode eval scope does not leak variable declarations to |
1303 // the caller's scope so we declare all locals, too. | 1312 // the caller's scope so we declare all locals, too. |
1304 if (top_scope_->is_function_scope() || | 1313 Scope* declaration_scope = DeclarationScope(); |
1305 top_scope_->is_strict_mode_eval_scope()) { | 1314 if (declaration_scope->is_function_scope() || |
1315 declaration_scope->is_strict_mode_eval_scope()) { | |
1306 // Declare the variable in the function scope. | 1316 // Declare the variable in the function scope. |
1307 var = top_scope_->LocalLookup(name); | 1317 var = declaration_scope->LocalLookup(name); |
1308 if (var == NULL) { | 1318 if (var == NULL) { |
1309 // Declare the name. | 1319 // Declare the name. |
1310 var = top_scope_->DeclareLocal(name, mode); | 1320 var = declaration_scope->DeclareLocal(name, mode); |
1311 } else { | 1321 } else { |
1312 // The name was declared before; check for conflicting | 1322 // The name was declared before; check for conflicting |
1313 // re-declarations. If the previous declaration was a const or the | 1323 // re-declarations. If the previous declaration was a const or the |
1314 // current declaration is a const then we have a conflict. There is | 1324 // current declaration is a const then we have a conflict. There is |
1315 // similar code in runtime.cc in the Declare functions. | 1325 // similar code in runtime.cc in the Declare functions. |
1316 if ((mode == Variable::CONST) || (var->mode() == Variable::CONST)) { | 1326 if ((mode == Variable::CONST) || (var->mode() == Variable::CONST)) { |
1317 // We only have vars and consts in declarations. | 1327 // We only have vars and consts in declarations. |
1318 ASSERT(var->mode() == Variable::VAR || | 1328 ASSERT(var->mode() == Variable::VAR || |
1319 var->mode() == Variable::CONST); | 1329 var->mode() == Variable::CONST); |
1320 const char* type = (var->mode() == Variable::VAR) ? "var" : "const"; | 1330 const char* type = (var->mode() == Variable::VAR) ? "var" : "const"; |
1321 Handle<String> type_string = | 1331 Handle<String> type_string = |
1322 isolate()->factory()->NewStringFromUtf8(CStrVector(type), TENURED); | 1332 isolate()->factory()->NewStringFromUtf8(CStrVector(type), TENURED); |
1323 Expression* expression = | 1333 Expression* expression = |
1324 NewThrowTypeError(isolate()->factory()->redeclaration_symbol(), | 1334 NewThrowTypeError(isolate()->factory()->redeclaration_symbol(), |
1325 type_string, name); | 1335 type_string, name); |
1326 top_scope_->SetIllegalRedeclaration(expression); | 1336 declaration_scope->SetIllegalRedeclaration(expression); |
1327 } | 1337 } |
1328 } | 1338 } |
1329 } | 1339 } |
1330 | 1340 |
1331 // We add a declaration node for every declaration. The compiler | 1341 // We add a declaration node for every declaration. The compiler |
1332 // will only generate code if necessary. In particular, declarations | 1342 // will only generate code if necessary. In particular, declarations |
1333 // for inner local variables that do not represent functions won't | 1343 // for inner local variables that do not represent functions won't |
1334 // result in any generated code. | 1344 // result in any generated code. |
1335 // | 1345 // |
1336 // Note that we always add an unresolved proxy even if it's not | 1346 // Note that we always add an unresolved proxy even if it's not |
1337 // used, simply because we don't know in this method (w/o extra | 1347 // used, simply because we don't know in this method (w/o extra |
1338 // parameters) if the proxy is needed or not. The proxy will be | 1348 // parameters) if the proxy is needed or not. The proxy will be |
1339 // bound during variable resolution time unless it was pre-bound | 1349 // bound during variable resolution time unless it was pre-bound |
1340 // below. | 1350 // below. |
1341 // | 1351 // |
1342 // WARNING: This will lead to multiple declaration nodes for the | 1352 // WARNING: This will lead to multiple declaration nodes for the |
1343 // same variable if it is declared several times. This is not a | 1353 // same variable if it is declared several times. This is not a |
1344 // semantic issue as long as we keep the source order, but it may be | 1354 // semantic issue as long as we keep the source order, but it may be |
1345 // a performance issue since it may lead to repeated | 1355 // a performance issue since it may lead to repeated |
1346 // Runtime::DeclareContextSlot() calls. | 1356 // Runtime::DeclareContextSlot() calls. |
1347 VariableProxy* proxy = top_scope_->NewUnresolved(name, inside_with()); | 1357 VariableProxy* proxy = declaration_scope->NewUnresolved(name, false); |
1348 top_scope_->AddDeclaration(new(zone()) Declaration(proxy, mode, fun)); | 1358 declaration_scope->AddDeclaration(new(zone()) Declaration(proxy, mode, fun)); |
1349 | 1359 |
1350 // For global const variables we bind the proxy to a variable. | 1360 // For global const variables we bind the proxy to a variable. |
1351 if (mode == Variable::CONST && top_scope_->is_global_scope()) { | 1361 if (mode == Variable::CONST && declaration_scope->is_global_scope()) { |
1352 ASSERT(resolve); // should be set by all callers | 1362 ASSERT(resolve); // should be set by all callers |
1353 Variable::Kind kind = Variable::NORMAL; | 1363 Variable::Kind kind = Variable::NORMAL; |
1354 var = new(zone()) Variable(top_scope_, name, Variable::CONST, true, kind); | 1364 var = new(zone()) Variable(declaration_scope, |
1365 name, | |
1366 Variable::CONST, | |
1367 true, | |
1368 kind); | |
1355 } | 1369 } |
1356 | 1370 |
1357 // If requested and we have a local variable, bind the proxy to the variable | 1371 // If requested and we have a local variable, bind the proxy to the variable |
1358 // at parse-time. This is used for functions (and consts) declared inside | 1372 // at parse-time. This is used for functions (and consts) declared inside |
1359 // statements: the corresponding function (or const) variable must be in the | 1373 // statements: the corresponding function (or const) variable must be in the |
1360 // function scope and not a statement-local scope, e.g. as provided with a | 1374 // function scope and not a statement-local scope, e.g. as provided with a |
1361 // 'with' statement: | 1375 // 'with' statement: |
1362 // | 1376 // |
1363 // with (obj) { | 1377 // with (obj) { |
1364 // function f() {} | 1378 // function f() {} |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1400 Expect(Token::COMMA, CHECK_OK); | 1414 Expect(Token::COMMA, CHECK_OK); |
1401 } | 1415 } |
1402 } | 1416 } |
1403 Expect(Token::RPAREN, CHECK_OK); | 1417 Expect(Token::RPAREN, CHECK_OK); |
1404 Expect(Token::SEMICOLON, CHECK_OK); | 1418 Expect(Token::SEMICOLON, CHECK_OK); |
1405 | 1419 |
1406 // Make sure that the function containing the native declaration | 1420 // Make sure that the function containing the native declaration |
1407 // isn't lazily compiled. The extension structures are only | 1421 // isn't lazily compiled. The extension structures are only |
1408 // accessible while parsing the first time not when reparsing | 1422 // accessible while parsing the first time not when reparsing |
1409 // because of lazy compilation. | 1423 // because of lazy compilation. |
1410 top_scope_->ForceEagerCompilation(); | 1424 DeclarationScope()->ForceEagerCompilation(); |
1411 | 1425 |
1412 // Compute the function template for the native function. | 1426 // Compute the function template for the native function. |
1413 v8::Handle<v8::FunctionTemplate> fun_template = | 1427 v8::Handle<v8::FunctionTemplate> fun_template = |
1414 extension_->GetNativeFunction(v8::Utils::ToLocal(name)); | 1428 extension_->GetNativeFunction(v8::Utils::ToLocal(name)); |
1415 ASSERT(!fun_template.IsEmpty()); | 1429 ASSERT(!fun_template.IsEmpty()); |
1416 | 1430 |
1417 // Instantiate the function and create a shared function info from it. | 1431 // Instantiate the function and create a shared function info from it. |
1418 Handle<JSFunction> fun = Utils::OpenHandle(*fun_template->GetFunction()); | 1432 Handle<JSFunction> fun = Utils::OpenHandle(*fun_template->GetFunction()); |
1419 const int literals = fun->NumberOfLiterals(); | 1433 const int literals = fun->NumberOfLiterals(); |
1420 Handle<Code> code = Handle<Code>(fun->shared()->code()); | 1434 Handle<Code> code = Handle<Code>(fun->shared()->code()); |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1478 } | 1492 } |
1479 Expect(Token::RBRACE, CHECK_OK); | 1493 Expect(Token::RBRACE, CHECK_OK); |
1480 return result; | 1494 return result; |
1481 } | 1495 } |
1482 | 1496 |
1483 | 1497 |
1484 Block* Parser::ParseVariableStatement(bool* ok) { | 1498 Block* Parser::ParseVariableStatement(bool* ok) { |
1485 // VariableStatement :: | 1499 // VariableStatement :: |
1486 // VariableDeclarations ';' | 1500 // VariableDeclarations ';' |
1487 | 1501 |
1488 Expression* dummy; // to satisfy the ParseVariableDeclarations() signature | 1502 Handle<String> ignore; |
1489 Block* result = ParseVariableDeclarations(true, &dummy, CHECK_OK); | 1503 Block* result = ParseVariableDeclarations(true, &ignore, CHECK_OK); |
1490 ExpectSemicolon(CHECK_OK); | 1504 ExpectSemicolon(CHECK_OK); |
1491 return result; | 1505 return result; |
1492 } | 1506 } |
1493 | 1507 |
1494 | 1508 |
1495 bool Parser::IsEvalOrArguments(Handle<String> string) { | 1509 bool Parser::IsEvalOrArguments(Handle<String> string) { |
1496 return string.is_identical_to(isolate()->factory()->eval_symbol()) || | 1510 return string.is_identical_to(isolate()->factory()->eval_symbol()) || |
1497 string.is_identical_to(isolate()->factory()->arguments_symbol()); | 1511 string.is_identical_to(isolate()->factory()->arguments_symbol()); |
1498 } | 1512 } |
1499 | 1513 |
1500 | 1514 |
1501 // If the variable declaration declares exactly one non-const | 1515 // If the variable declaration declares exactly one non-const |
1502 // variable, then *var is set to that variable. In all other cases, | 1516 // variable, then *var is set to that variable. In all other cases, |
1503 // *var is untouched; in particular, it is the caller's responsibility | 1517 // *var is untouched; in particular, it is the caller's responsibility |
1504 // to initialize it properly. This mechanism is used for the parsing | 1518 // to initialize it properly. This mechanism is used for the parsing |
1505 // of 'for-in' loops. | 1519 // of 'for-in' loops. |
1506 Block* Parser::ParseVariableDeclarations(bool accept_IN, | 1520 Block* Parser::ParseVariableDeclarations(bool accept_IN, |
1507 Expression** var, | 1521 Handle<String>* name, |
Kevin Millikin (Chromium)
2011/06/30 09:28:45
In most cases (all but 'for (var ... in ...)' the
| |
1508 bool* ok) { | 1522 bool* ok) { |
1509 // VariableDeclarations :: | 1523 // VariableDeclarations :: |
1510 // ('var' | 'const') (Identifier ('=' AssignmentExpression)?)+[','] | 1524 // ('var' | 'const') (Identifier ('=' AssignmentExpression)?)+[','] |
1511 | 1525 |
1512 Variable::Mode mode = Variable::VAR; | 1526 Variable::Mode mode = Variable::VAR; |
1513 bool is_const = false; | 1527 bool is_const = false; |
1528 Scope* declaration_scope = DeclarationScope(); | |
1514 if (peek() == Token::VAR) { | 1529 if (peek() == Token::VAR) { |
1515 Consume(Token::VAR); | 1530 Consume(Token::VAR); |
1516 } else if (peek() == Token::CONST) { | 1531 } else if (peek() == Token::CONST) { |
1517 Consume(Token::CONST); | 1532 Consume(Token::CONST); |
1518 if (top_scope_->is_strict_mode()) { | 1533 if (declaration_scope->is_strict_mode()) { |
1519 ReportMessage("strict_const", Vector<const char*>::empty()); | 1534 ReportMessage("strict_const", Vector<const char*>::empty()); |
1520 *ok = false; | 1535 *ok = false; |
1521 return NULL; | 1536 return NULL; |
1522 } | 1537 } |
1523 mode = Variable::CONST; | 1538 mode = Variable::CONST; |
1524 is_const = true; | 1539 is_const = true; |
1525 } else { | 1540 } else { |
1526 UNREACHABLE(); // by current callers | 1541 UNREACHABLE(); // by current callers |
1527 } | 1542 } |
1528 | 1543 |
1529 // The scope of a variable/const declared anywhere inside a function | 1544 // The scope of a variable/const declared anywhere inside a function |
1530 // is the entire function (ECMA-262, 3rd, 10.1.3, and 12.2). Thus we can | 1545 // is the entire function (ECMA-262, 3rd, 10.1.3, and 12.2). Thus we can |
1531 // transform a source-level variable/const declaration into a (Function) | 1546 // transform a source-level variable/const declaration into a (Function) |
1532 // Scope declaration, and rewrite the source-level initialization into an | 1547 // Scope declaration, and rewrite the source-level initialization into an |
1533 // assignment statement. We use a block to collect multiple assignments. | 1548 // assignment statement. We use a block to collect multiple assignments. |
1534 // | 1549 // |
1535 // We mark the block as initializer block because we don't want the | 1550 // We mark the block as initializer block because we don't want the |
1536 // rewriter to add a '.result' assignment to such a block (to get compliant | 1551 // rewriter to add a '.result' assignment to such a block (to get compliant |
1537 // behavior for code such as print(eval('var x = 7')), and for cosmetic | 1552 // behavior for code such as print(eval('var x = 7')), and for cosmetic |
1538 // reasons when pretty-printing. Also, unless an assignment (initialization) | 1553 // reasons when pretty-printing. Also, unless an assignment (initialization) |
1539 // is inside an initializer block, it is ignored. | 1554 // is inside an initializer block, it is ignored. |
1540 // | 1555 // |
1541 // Create new block with one expected declaration. | 1556 // Create new block with one expected declaration. |
1542 Block* block = new(zone()) Block(NULL, 1, true); | 1557 Block* block = new(zone()) Block(NULL, 1, true); |
1543 VariableProxy* last_var = NULL; // the last variable declared | |
1544 int nvars = 0; // the number of variables declared | 1558 int nvars = 0; // the number of variables declared |
1545 do { | 1559 do { |
1546 if (fni_ != NULL) fni_->Enter(); | 1560 if (fni_ != NULL) fni_->Enter(); |
1547 | 1561 |
1548 // Parse variable name. | 1562 // Parse variable name. |
1549 if (nvars > 0) Consume(Token::COMMA); | 1563 if (nvars > 0) Consume(Token::COMMA); |
1550 Handle<String> name = ParseIdentifier(CHECK_OK); | 1564 *name = ParseIdentifier(CHECK_OK); |
1551 if (fni_ != NULL) fni_->PushVariableName(name); | 1565 if (fni_ != NULL) fni_->PushVariableName(*name); |
1552 | 1566 |
1553 // Strict mode variables may not be named eval or arguments | 1567 // Strict mode variables may not be named eval or arguments |
1554 if (top_scope_->is_strict_mode() && IsEvalOrArguments(name)) { | 1568 if (declaration_scope->is_strict_mode() && IsEvalOrArguments(*name)) { |
1555 ReportMessage("strict_var_name", Vector<const char*>::empty()); | 1569 ReportMessage("strict_var_name", Vector<const char*>::empty()); |
1556 *ok = false; | 1570 *ok = false; |
1557 return NULL; | 1571 return NULL; |
1558 } | 1572 } |
1559 | 1573 |
1560 // Declare variable. | 1574 // Declare variable. |
1561 // Note that we *always* must treat the initial value via a separate init | 1575 // Note that we *always* must treat the initial value via a separate init |
1562 // assignment for variables and constants because the value must be assigned | 1576 // assignment for variables and constants because the value must be assigned |
1563 // when the variable is encountered in the source. But the variable/constant | 1577 // when the variable is encountered in the source. But the variable/constant |
1564 // is declared (and set to 'undefined') upon entering the function within | 1578 // is declared (and set to 'undefined') upon entering the function within |
1565 // which the variable or constant is declared. Only function variables have | 1579 // which the variable or constant is declared. Only function variables have |
1566 // an initial value in the declaration (because they are initialized upon | 1580 // an initial value in the declaration (because they are initialized upon |
1567 // entering the function). | 1581 // entering the function). |
1568 // | 1582 // |
1569 // If we have a const declaration, in an inner scope, the proxy is always | 1583 // If we have a const declaration, in an inner scope, the proxy is always |
1570 // bound to the declared variable (independent of possibly surrounding with | 1584 // bound to the declared variable (independent of possibly surrounding with |
1571 // statements). | 1585 // statements). |
1572 last_var = Declare(name, mode, NULL, | 1586 Declare(*name, mode, NULL, is_const /* always bound for CONST! */, |
1573 is_const /* always bound for CONST! */, | 1587 CHECK_OK); |
1574 CHECK_OK); | |
1575 nvars++; | 1588 nvars++; |
1576 if (top_scope_->num_var_or_const() > kMaxNumFunctionLocals) { | 1589 if (declaration_scope->num_var_or_const() > kMaxNumFunctionLocals) { |
1577 ReportMessageAt(scanner().location(), "too_many_variables", | 1590 ReportMessageAt(scanner().location(), "too_many_variables", |
1578 Vector<const char*>::empty()); | 1591 Vector<const char*>::empty()); |
1579 *ok = false; | 1592 *ok = false; |
1580 return NULL; | 1593 return NULL; |
1581 } | 1594 } |
1582 | 1595 |
1583 // Parse initialization expression if present and/or needed. A | 1596 // Parse initialization expression if present and/or needed. A |
1584 // declaration of the form: | 1597 // declaration of the form: |
1585 // | 1598 // |
1586 // var v = x; | 1599 // var v = x; |
1587 // | 1600 // |
1588 // is syntactic sugar for: | 1601 // is syntactic sugar for: |
1589 // | 1602 // |
1590 // var v; v = x; | 1603 // var v; v = x; |
1591 // | 1604 // |
1592 // In particular, we need to re-lookup 'v' as it may be a | 1605 // In particular, we need to re-lookup 'v' (in top_scope_, not |
1593 // different 'v' than the 'v' in the declaration (if we are inside | 1606 // declaration_scope) as it may be a different 'v' than the 'v' in the |
1594 // a 'with' statement that makes a object property with name 'v' | 1607 // declaration (e.g., if we are inside a 'with' statement or 'catch' |
1595 // visible). | 1608 // block). |
1596 // | 1609 // |
1597 // However, note that const declarations are different! A const | 1610 // However, note that const declarations are different! A const |
1598 // declaration of the form: | 1611 // declaration of the form: |
1599 // | 1612 // |
1600 // const c = x; | 1613 // const c = x; |
1601 // | 1614 // |
1602 // is *not* syntactic sugar for: | 1615 // is *not* syntactic sugar for: |
1603 // | 1616 // |
1604 // const c; c = x; | 1617 // const c; c = x; |
1605 // | 1618 // |
1606 // The "variable" c initialized to x is the same as the declared | 1619 // The "variable" c initialized to x is the same as the declared |
1607 // one - there is no re-lookup (see the last parameter of the | 1620 // one - there is no re-lookup (see the last parameter of the |
1608 // Declare() call above). | 1621 // Declare() call above). |
1609 | 1622 |
1623 Scope* initialization_scope = is_const ? declaration_scope : top_scope_; | |
Kevin Millikin (Chromium)
2011/06/30 09:28:45
It's subtle that the declaration and initializatio
| |
1610 Expression* value = NULL; | 1624 Expression* value = NULL; |
1611 int position = -1; | 1625 int position = -1; |
1612 if (peek() == Token::ASSIGN) { | 1626 if (peek() == Token::ASSIGN) { |
1613 Expect(Token::ASSIGN, CHECK_OK); | 1627 Expect(Token::ASSIGN, CHECK_OK); |
1614 position = scanner().location().beg_pos; | 1628 position = scanner().location().beg_pos; |
1615 value = ParseAssignmentExpression(accept_IN, CHECK_OK); | 1629 value = ParseAssignmentExpression(accept_IN, CHECK_OK); |
1616 // Don't infer if it is "a = function(){...}();"-like expression. | 1630 // Don't infer if it is "a = function(){...}();"-like expression. |
1617 if (fni_ != NULL && | 1631 if (fni_ != NULL && |
1618 value->AsCall() == NULL && | 1632 value->AsCall() == NULL && |
1619 value->AsCallNew() == NULL) { | 1633 value->AsCallNew() == NULL) { |
(...skipping 20 matching lines...) Expand all Loading... | |
1640 // | 1654 // |
1641 // Executing the variable declaration statement will always | 1655 // Executing the variable declaration statement will always |
1642 // guarantee to give the global object a "local" variable; a | 1656 // guarantee to give the global object a "local" variable; a |
1643 // variable defined in the global object and not in any | 1657 // variable defined in the global object and not in any |
1644 // prototype. This way, global variable declarations can shadow | 1658 // prototype. This way, global variable declarations can shadow |
1645 // properties in the prototype chain, but only after the variable | 1659 // properties in the prototype chain, but only after the variable |
1646 // declaration statement has been executed. This is important in | 1660 // declaration statement has been executed. This is important in |
1647 // browsers where the global object (window) has lots of | 1661 // browsers where the global object (window) has lots of |
1648 // properties defined in prototype objects. | 1662 // properties defined in prototype objects. |
1649 | 1663 |
1650 if (top_scope_->is_global_scope()) { | 1664 if (initialization_scope->is_global_scope()) { |
1651 // Compute the arguments for the runtime call. | 1665 // Compute the arguments for the runtime call. |
1652 ZoneList<Expression*>* arguments = new(zone()) ZoneList<Expression*>(3); | 1666 ZoneList<Expression*>* arguments = new(zone()) ZoneList<Expression*>(3); |
1653 // We have at least 1 parameter. | 1667 // We have at least 1 parameter. |
1654 arguments->Add(new(zone()) Literal(name)); | 1668 arguments->Add(new(zone()) Literal(*name)); |
1655 CallRuntime* initialize; | 1669 CallRuntime* initialize; |
1656 | 1670 |
1657 if (is_const) { | 1671 if (is_const) { |
1658 arguments->Add(value); | 1672 arguments->Add(value); |
1659 value = NULL; // zap the value to avoid the unnecessary assignment | 1673 value = NULL; // zap the value to avoid the unnecessary assignment |
1660 | 1674 |
1661 // Construct the call to Runtime_InitializeConstGlobal | 1675 // Construct the call to Runtime_InitializeConstGlobal |
1662 // and add it to the initialization statement block. | 1676 // and add it to the initialization statement block. |
1663 // Note that the function does different things depending on | 1677 // Note that the function does different things depending on |
1664 // the number of arguments (1 or 2). | 1678 // the number of arguments (1 or 2). |
1665 initialize = | 1679 initialize = |
1666 new(zone()) CallRuntime( | 1680 new(zone()) CallRuntime( |
1667 isolate()->factory()->InitializeConstGlobal_symbol(), | 1681 isolate()->factory()->InitializeConstGlobal_symbol(), |
1668 Runtime::FunctionForId(Runtime::kInitializeConstGlobal), | 1682 Runtime::FunctionForId(Runtime::kInitializeConstGlobal), |
1669 arguments); | 1683 arguments); |
1670 } else { | 1684 } else { |
1671 // Add strict mode. | 1685 // Add strict mode. |
1672 // We may want to pass singleton to avoid Literal allocations. | 1686 // We may want to pass singleton to avoid Literal allocations. |
1673 arguments->Add(NewNumberLiteral( | 1687 StrictModeFlag flag = initialization_scope->is_strict_mode() |
1674 top_scope_->is_strict_mode() ? kStrictMode : kNonStrictMode)); | 1688 ? kStrictMode |
1689 : kNonStrictMode; | |
1690 arguments->Add(NewNumberLiteral(flag)); | |
1675 | 1691 |
1676 // Be careful not to assign a value to the global variable if | 1692 // Be careful not to assign a value to the global variable if |
1677 // we're in a with. The initialization value should not | 1693 // we're in a with. The initialization value should not |
1678 // necessarily be stored in the global object in that case, | 1694 // necessarily be stored in the global object in that case, |
1679 // which is why we need to generate a separate assignment node. | 1695 // which is why we need to generate a separate assignment node. |
1680 if (value != NULL && !inside_with()) { | 1696 if (value != NULL && !inside_with()) { |
1681 arguments->Add(value); | 1697 arguments->Add(value); |
1682 value = NULL; // zap the value to avoid the unnecessary assignment | 1698 value = NULL; // zap the value to avoid the unnecessary assignment |
1683 } | 1699 } |
1684 | 1700 |
(...skipping 16 matching lines...) Expand all Loading... | |
1701 // between variables and constants: Variable initializations are simply | 1717 // between variables and constants: Variable initializations are simply |
1702 // assignments (with all the consequences if they are inside a 'with' | 1718 // assignments (with all the consequences if they are inside a 'with' |
1703 // statement - they may change a 'with' object property). Constant | 1719 // statement - they may change a 'with' object property). Constant |
1704 // initializations always assign to the declared constant which is | 1720 // initializations always assign to the declared constant which is |
1705 // always at the function scope level. This is only relevant for | 1721 // always at the function scope level. This is only relevant for |
1706 // dynamically looked-up variables and constants (the start context | 1722 // dynamically looked-up variables and constants (the start context |
1707 // for constant lookups is always the function context, while it is | 1723 // for constant lookups is always the function context, while it is |
1708 // the top context for variables). Sigh... | 1724 // the top context for variables). Sigh... |
1709 if (value != NULL) { | 1725 if (value != NULL) { |
1710 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR); | 1726 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR); |
1727 bool in_with = is_const ? false : inside_with(); | |
1728 VariableProxy* proxy = | |
1729 initialization_scope->NewUnresolved(*name, in_with); | |
1711 Assignment* assignment = | 1730 Assignment* assignment = |
1712 new(zone()) Assignment(op, last_var, value, position); | 1731 new(zone()) Assignment(op, proxy, value, position); |
1713 if (block) { | 1732 if (block) { |
1714 block->AddStatement(new(zone()) ExpressionStatement(assignment)); | 1733 block->AddStatement(new(zone()) ExpressionStatement(assignment)); |
1715 } | 1734 } |
1716 } | 1735 } |
1717 | 1736 |
1718 if (fni_ != NULL) fni_->Leave(); | 1737 if (fni_ != NULL) fni_->Leave(); |
1719 } while (peek() == Token::COMMA); | 1738 } while (peek() == Token::COMMA); |
1720 | 1739 |
1721 if (!is_const && nvars == 1) { | |
1722 // We have a single, non-const variable. | |
1723 ASSERT(last_var != NULL); | |
1724 *var = last_var; | |
1725 } | |
1726 | |
1727 return block; | 1740 return block; |
1728 } | 1741 } |
1729 | 1742 |
1730 | 1743 |
1731 static bool ContainsLabel(ZoneStringList* labels, Handle<String> label) { | 1744 static bool ContainsLabel(ZoneStringList* labels, Handle<String> label) { |
1732 ASSERT(!label.is_null()); | 1745 ASSERT(!label.is_null()); |
1733 if (labels != NULL) | 1746 if (labels != NULL) |
1734 for (int i = labels->length(); i-- > 0; ) | 1747 for (int i = labels->length(); i-- > 0; ) |
1735 if (labels->at(i).is_identical_to(label)) | 1748 if (labels->at(i).is_identical_to(label)) |
1736 return true; | 1749 return true; |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1888 // Consume the return token. It is necessary to do the before | 1901 // Consume the return token. It is necessary to do the before |
1889 // reporting any errors on it, because of the way errors are | 1902 // reporting any errors on it, because of the way errors are |
1890 // reported (underlining). | 1903 // reported (underlining). |
1891 Expect(Token::RETURN, CHECK_OK); | 1904 Expect(Token::RETURN, CHECK_OK); |
1892 | 1905 |
1893 // An ECMAScript program is considered syntactically incorrect if it | 1906 // An ECMAScript program is considered syntactically incorrect if it |
1894 // contains a return statement that is not within the body of a | 1907 // contains a return statement that is not within the body of a |
1895 // function. See ECMA-262, section 12.9, page 67. | 1908 // function. See ECMA-262, section 12.9, page 67. |
1896 // | 1909 // |
1897 // To be consistent with KJS we report the syntax error at runtime. | 1910 // To be consistent with KJS we report the syntax error at runtime. |
1898 if (!top_scope_->is_function_scope()) { | 1911 Scope* declaration_scope = DeclarationScope(); |
1912 if (declaration_scope->is_global_scope() || | |
1913 declaration_scope->is_eval_scope()) { | |
1899 Handle<String> type = isolate()->factory()->illegal_return_symbol(); | 1914 Handle<String> type = isolate()->factory()->illegal_return_symbol(); |
1900 Expression* throw_error = NewThrowSyntaxError(type, Handle<Object>::null()); | 1915 Expression* throw_error = NewThrowSyntaxError(type, Handle<Object>::null()); |
1901 return new(zone()) ExpressionStatement(throw_error); | 1916 return new(zone()) ExpressionStatement(throw_error); |
1902 } | 1917 } |
1903 | 1918 |
1904 Token::Value tok = peek(); | 1919 Token::Value tok = peek(); |
1905 if (scanner().HasAnyLineTerminatorBeforeNext() || | 1920 if (scanner().HasAnyLineTerminatorBeforeNext() || |
1906 tok == Token::SEMICOLON || | 1921 tok == Token::SEMICOLON || |
1907 tok == Token::RBRACE || | 1922 tok == Token::RBRACE || |
1908 tok == Token::EOS) { | 1923 tok == Token::EOS) { |
1909 ExpectSemicolon(CHECK_OK); | 1924 ExpectSemicolon(CHECK_OK); |
1910 return new(zone()) ReturnStatement(GetLiteralUndefined()); | 1925 return new(zone()) ReturnStatement(GetLiteralUndefined()); |
1911 } | 1926 } |
1912 | 1927 |
1913 Expression* expr = ParseExpression(true, CHECK_OK); | 1928 Expression* expr = ParseExpression(true, CHECK_OK); |
1914 ExpectSemicolon(CHECK_OK); | 1929 ExpectSemicolon(CHECK_OK); |
1915 return new(zone()) ReturnStatement(expr); | 1930 return new(zone()) ReturnStatement(expr); |
1916 } | 1931 } |
1917 | 1932 |
1918 | 1933 |
1919 Block* Parser::WithHelper(Expression* obj, ZoneStringList* labels, bool* ok) { | 1934 Block* Parser::WithHelper(Expression* obj, ZoneStringList* labels, bool* ok) { |
1920 // Parse the statement and collect escaping labels. | 1935 // Parse the statement and collect escaping labels. |
1921 TargetCollector collector; | 1936 TargetCollector collector; |
1922 Statement* stat; | 1937 Statement* stat; |
1923 { Target target(&this->target_stack_, &collector); | 1938 { Target target(&this->target_stack_, &collector); |
1924 with_nesting_level_++; | 1939 with_nesting_level_++; |
1925 top_scope_->RecordWithStatement(); | 1940 DeclarationScope()->RecordWithStatement(); |
Kevin Millikin (Chromium)
2011/06/30 09:28:45
This is wrong, let's talk about what to do here.
Mads Ager (chromium)
2011/06/30 12:08:32
But it is safe, right?
| |
1926 stat = ParseStatement(labels, CHECK_OK); | 1941 stat = ParseStatement(labels, CHECK_OK); |
1927 with_nesting_level_--; | 1942 with_nesting_level_--; |
1928 } | 1943 } |
1929 // Create resulting block with two statements. | 1944 // Create resulting block with two statements. |
1930 // 1: Evaluate the with expression. | 1945 // 1: Evaluate the with expression. |
1931 // 2: The try-finally block evaluating the body. | 1946 // 2: The try-finally block evaluating the body. |
1932 Block* result = new(zone()) Block(NULL, 2, false); | 1947 Block* result = new(zone()) Block(NULL, 2, false); |
1933 | 1948 |
1934 if (result != NULL) { | 1949 if (result != NULL) { |
1935 result->AddStatement(new(zone()) EnterWithContextStatement(obj)); | 1950 result->AddStatement(new(zone()) EnterWithContextStatement(obj)); |
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2075 ReportMessage("no_catch_or_finally", Vector<const char*>::empty()); | 2090 ReportMessage("no_catch_or_finally", Vector<const char*>::empty()); |
2076 *ok = false; | 2091 *ok = false; |
2077 return NULL; | 2092 return NULL; |
2078 } | 2093 } |
2079 | 2094 |
2080 // If we can break out from the catch block and there is a finally block, | 2095 // If we can break out from the catch block and there is a finally block, |
2081 // then we will need to collect escaping targets from the catch | 2096 // then we will need to collect escaping targets from the catch |
2082 // block. Since we don't know yet if there will be a finally block, we | 2097 // block. Since we don't know yet if there will be a finally block, we |
2083 // always collect the targets. | 2098 // always collect the targets. |
2084 TargetCollector catch_collector; | 2099 TargetCollector catch_collector; |
2100 Scope* catch_scope = NULL; | |
2101 Variable* catch_variable = NULL; | |
2085 Block* catch_block = NULL; | 2102 Block* catch_block = NULL; |
2086 Handle<String> name; | 2103 Handle<String> name; |
2087 if (tok == Token::CATCH) { | 2104 if (tok == Token::CATCH) { |
2088 Consume(Token::CATCH); | 2105 Consume(Token::CATCH); |
2089 | 2106 |
2090 Expect(Token::LPAREN, CHECK_OK); | 2107 Expect(Token::LPAREN, CHECK_OK); |
2091 name = ParseIdentifier(CHECK_OK); | 2108 name = ParseIdentifier(CHECK_OK); |
2092 | 2109 |
2093 if (top_scope_->is_strict_mode() && IsEvalOrArguments(name)) { | 2110 if (top_scope_->is_strict_mode() && IsEvalOrArguments(name)) { |
2094 ReportMessage("strict_catch_variable", Vector<const char*>::empty()); | 2111 ReportMessage("strict_catch_variable", Vector<const char*>::empty()); |
2095 *ok = false; | 2112 *ok = false; |
2096 return NULL; | 2113 return NULL; |
2097 } | 2114 } |
2098 | 2115 |
2099 Expect(Token::RPAREN, CHECK_OK); | 2116 Expect(Token::RPAREN, CHECK_OK); |
2100 | 2117 |
2101 if (peek() == Token::LBRACE) { | 2118 if (peek() == Token::LBRACE) { |
2102 // Rewrite the catch body B to a single statement block | 2119 // Rewrite the catch body B to a single statement block |
2103 // { try B finally { PopContext }}. | 2120 // { try B finally { PopContext }}. |
2104 Block* inner_body; | 2121 Block* inner_body; |
2105 // We need to collect escapes from the body for both the inner | 2122 // We need to collect escapes from the body for both the inner |
2106 // try/finally used to pop the catch context and any possible outer | 2123 // try/finally used to pop the catch context and any possible outer |
2107 // try/finally. | 2124 // try/finally. |
2108 TargetCollector inner_collector; | 2125 TargetCollector inner_collector; |
2109 { Target target(&this->target_stack_, &catch_collector); | 2126 { Target target(&this->target_stack_, &catch_collector); |
2110 { Target target(&this->target_stack_, &inner_collector); | 2127 { Target target(&this->target_stack_, &inner_collector); |
2111 ++with_nesting_level_; | 2128 catch_scope = NewScope(top_scope_, Scope::CATCH_SCOPE, inside_with()); |
2112 top_scope_->RecordWithStatement(); | 2129 if (top_scope_->is_strict_mode()) { |
2130 catch_scope->EnableStrictMode(); | |
2131 } | |
2132 catch_variable = catch_scope->DeclareLocal(name, Variable::VAR); | |
2133 | |
2134 Scope* saved_scope = top_scope_; | |
2135 top_scope_ = catch_scope; | |
2113 inner_body = ParseBlock(NULL, CHECK_OK); | 2136 inner_body = ParseBlock(NULL, CHECK_OK); |
2114 --with_nesting_level_; | 2137 top_scope_ = saved_scope; |
2115 } | 2138 } |
2116 } | 2139 } |
2117 | 2140 |
2118 // Create exit block. | 2141 // Create exit block. |
2119 Block* inner_finally = new(zone()) Block(NULL, 1, false); | 2142 Block* inner_finally = new(zone()) Block(NULL, 1, false); |
2120 inner_finally->AddStatement(new(zone()) ExitContextStatement()); | 2143 inner_finally->AddStatement(new(zone()) ExitContextStatement()); |
2121 | 2144 |
2122 // Create a try/finally statement. | 2145 // Create a try/finally statement. |
2123 TryFinallyStatement* inner_try_finally = | 2146 TryFinallyStatement* inner_try_finally = |
2124 new(zone()) TryFinallyStatement(inner_body, inner_finally); | 2147 new(zone()) TryFinallyStatement(inner_body, inner_finally); |
(...skipping 13 matching lines...) Expand all Loading... | |
2138 Consume(Token::FINALLY); | 2161 Consume(Token::FINALLY); |
2139 finally_block = ParseBlock(NULL, CHECK_OK); | 2162 finally_block = ParseBlock(NULL, CHECK_OK); |
2140 } | 2163 } |
2141 | 2164 |
2142 // Simplify the AST nodes by converting: | 2165 // Simplify the AST nodes by converting: |
2143 // 'try B0 catch B1 finally B2' | 2166 // 'try B0 catch B1 finally B2' |
2144 // to: | 2167 // to: |
2145 // 'try { try B0 catch B1 } finally B2' | 2168 // 'try { try B0 catch B1 } finally B2' |
2146 | 2169 |
2147 if (catch_block != NULL && finally_block != NULL) { | 2170 if (catch_block != NULL && finally_block != NULL) { |
2171 // If we have both, create an inner try/catch. | |
2172 ASSERT(catch_scope != NULL && catch_variable != NULL); | |
2148 TryCatchStatement* statement = | 2173 TryCatchStatement* statement = |
2149 new(zone()) TryCatchStatement(try_block, name, catch_block); | 2174 new(zone()) TryCatchStatement(try_block, |
2175 catch_scope, | |
2176 catch_variable, | |
2177 catch_block); | |
2150 statement->set_escaping_targets(try_collector.targets()); | 2178 statement->set_escaping_targets(try_collector.targets()); |
2151 try_block = new(zone()) Block(NULL, 1, false); | 2179 try_block = new(zone()) Block(NULL, 1, false); |
2152 try_block->AddStatement(statement); | 2180 try_block->AddStatement(statement); |
2153 catch_block = NULL; | 2181 catch_block = NULL; // Clear to indicate it's been handled. |
2154 } | 2182 } |
2155 | 2183 |
2156 TryStatement* result = NULL; | 2184 TryStatement* result = NULL; |
2157 if (catch_block != NULL) { | 2185 if (catch_block != NULL) { |
2158 ASSERT(finally_block == NULL); | 2186 ASSERT(finally_block == NULL); |
2187 ASSERT(catch_scope != NULL && catch_variable != NULL); | |
2159 result = | 2188 result = |
2160 new(zone()) TryCatchStatement(try_block, name, catch_block); | 2189 new(zone()) TryCatchStatement(try_block, |
2190 catch_scope, | |
2191 catch_variable, | |
2192 catch_block); | |
2161 } else { | 2193 } else { |
2162 ASSERT(finally_block != NULL); | 2194 ASSERT(finally_block != NULL); |
2163 result = new(zone()) TryFinallyStatement(try_block, finally_block); | 2195 result = new(zone()) TryFinallyStatement(try_block, finally_block); |
2164 // Combine the jump targets of the try block and the possible catch block. | 2196 // Combine the jump targets of the try block and the possible catch block. |
2165 try_collector.targets()->AddAll(*catch_collector.targets()); | 2197 try_collector.targets()->AddAll(*catch_collector.targets()); |
2166 } | 2198 } |
2167 | 2199 |
2168 result->set_escaping_targets(try_collector.targets()); | 2200 result->set_escaping_targets(try_collector.targets()); |
2169 return result; | 2201 return result; |
2170 } | 2202 } |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2223 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) { | 2255 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) { |
2224 // ForStatement :: | 2256 // ForStatement :: |
2225 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement | 2257 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement |
2226 | 2258 |
2227 Statement* init = NULL; | 2259 Statement* init = NULL; |
2228 | 2260 |
2229 Expect(Token::FOR, CHECK_OK); | 2261 Expect(Token::FOR, CHECK_OK); |
2230 Expect(Token::LPAREN, CHECK_OK); | 2262 Expect(Token::LPAREN, CHECK_OK); |
2231 if (peek() != Token::SEMICOLON) { | 2263 if (peek() != Token::SEMICOLON) { |
2232 if (peek() == Token::VAR || peek() == Token::CONST) { | 2264 if (peek() == Token::VAR || peek() == Token::CONST) { |
2233 Expression* each = NULL; | 2265 Handle<String> name; |
2234 Block* variable_statement = | 2266 Block* variable_statement = |
2235 ParseVariableDeclarations(false, &each, CHECK_OK); | 2267 ParseVariableDeclarations(false, &name, CHECK_OK); |
2268 VariableProxy* each = top_scope_->NewUnresolved(name, inside_with()); | |
2269 | |
2236 if (peek() == Token::IN && each != NULL) { | 2270 if (peek() == Token::IN && each != NULL) { |
2237 ForInStatement* loop = new(zone()) ForInStatement(labels); | 2271 ForInStatement* loop = new(zone()) ForInStatement(labels); |
2238 Target target(&this->target_stack_, loop); | 2272 Target target(&this->target_stack_, loop); |
2239 | 2273 |
2240 Expect(Token::IN, CHECK_OK); | 2274 Expect(Token::IN, CHECK_OK); |
2241 Expression* enumerable = ParseExpression(true, CHECK_OK); | 2275 Expression* enumerable = ParseExpression(true, CHECK_OK); |
2242 Expect(Token::RPAREN, CHECK_OK); | 2276 Expect(Token::RPAREN, CHECK_OK); |
2243 | 2277 |
2244 Statement* body = ParseStatement(NULL, CHECK_OK); | 2278 Statement* body = ParseStatement(NULL, CHECK_OK); |
2245 loop->Initialize(each, enumerable, body); | 2279 loop->Initialize(each, enumerable, body); |
(...skipping 648 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2894 // String | 2928 // String |
2895 // ArrayLiteral | 2929 // ArrayLiteral |
2896 // ObjectLiteral | 2930 // ObjectLiteral |
2897 // RegExpLiteral | 2931 // RegExpLiteral |
2898 // '(' Expression ')' | 2932 // '(' Expression ')' |
2899 | 2933 |
2900 Expression* result = NULL; | 2934 Expression* result = NULL; |
2901 switch (peek()) { | 2935 switch (peek()) { |
2902 case Token::THIS: { | 2936 case Token::THIS: { |
2903 Consume(Token::THIS); | 2937 Consume(Token::THIS); |
2904 VariableProxy* recv = top_scope_->receiver(); | 2938 result = new(zone()) VariableProxy(top_scope_->receiver()); |
2905 result = recv; | |
2906 break; | 2939 break; |
2907 } | 2940 } |
2908 | 2941 |
2909 case Token::NULL_LITERAL: | 2942 case Token::NULL_LITERAL: |
2910 Consume(Token::NULL_LITERAL); | 2943 Consume(Token::NULL_LITERAL); |
2911 result = new(zone()) Literal(isolate()->factory()->null_value()); | 2944 result = new(zone()) Literal(isolate()->factory()->null_value()); |
2912 break; | 2945 break; |
2913 | 2946 |
2914 case Token::TRUE_LITERAL: | 2947 case Token::TRUE_LITERAL: |
2915 Consume(Token::TRUE_LITERAL); | 2948 Consume(Token::TRUE_LITERAL); |
(...skipping 839 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3755 // CallRuntime :: | 3788 // CallRuntime :: |
3756 // '%' Identifier Arguments | 3789 // '%' Identifier Arguments |
3757 | 3790 |
3758 Expect(Token::MOD, CHECK_OK); | 3791 Expect(Token::MOD, CHECK_OK); |
3759 Handle<String> name = ParseIdentifier(CHECK_OK); | 3792 Handle<String> name = ParseIdentifier(CHECK_OK); |
3760 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); | 3793 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); |
3761 | 3794 |
3762 if (extension_ != NULL) { | 3795 if (extension_ != NULL) { |
3763 // The extension structures are only accessible while parsing the | 3796 // The extension structures are only accessible while parsing the |
3764 // very first time not when reparsing because of lazy compilation. | 3797 // very first time not when reparsing because of lazy compilation. |
3765 top_scope_->ForceEagerCompilation(); | 3798 DeclarationScope()->ForceEagerCompilation(); |
3766 } | 3799 } |
3767 | 3800 |
3768 const Runtime::Function* function = Runtime::FunctionForSymbol(name); | 3801 const Runtime::Function* function = Runtime::FunctionForSymbol(name); |
3769 | 3802 |
3770 // Check for built-in IS_VAR macro. | 3803 // Check for built-in IS_VAR macro. |
3771 if (function != NULL && | 3804 if (function != NULL && |
3772 function->intrinsic_type == Runtime::RUNTIME && | 3805 function->intrinsic_type == Runtime::RUNTIME && |
3773 function->function_id == Runtime::kIS_VAR) { | 3806 function->function_id == Runtime::kIS_VAR) { |
3774 // %IS_VAR(x) evaluates to x if x is a variable, | 3807 // %IS_VAR(x) evaluates to x if x is a variable, |
3775 // leads to a parse error otherwise. Could be implemented as an | 3808 // leads to a parse error otherwise. Could be implemented as an |
(...skipping 1259 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5035 info->is_global(), | 5068 info->is_global(), |
5036 info->StrictMode()); | 5069 info->StrictMode()); |
5037 } | 5070 } |
5038 } | 5071 } |
5039 | 5072 |
5040 info->SetFunction(result); | 5073 info->SetFunction(result); |
5041 return (result != NULL); | 5074 return (result != NULL); |
5042 } | 5075 } |
5043 | 5076 |
5044 } } // namespace v8::internal | 5077 } } // namespace v8::internal |
OLD | NEW |