Index: src/compiler.cc |
=================================================================== |
--- src/compiler.cc (revision 3642) |
+++ src/compiler.cc (working copy) |
@@ -46,25 +46,11 @@ |
public: |
enum CodeGenTag { NORMAL, FAST }; |
- CodeGenSelector() |
- : has_supported_syntax_(true), |
- context_(Expression::kUninitialized) { |
- } |
+ CodeGenSelector() : has_supported_syntax_(true) {} |
CodeGenTag Select(FunctionLiteral* fun); |
private: |
- // Visit an expression in a given expression context. |
- void ProcessExpression(Expression* expr, Expression::Context context) { |
- ASSERT(expr->context() == Expression::kUninitialized || |
- expr->context() == context); |
- Expression::Context saved = context_; |
- context_ = context; |
- Visit(expr); |
- expr->set_context(context); |
- context_ = saved; |
- } |
- |
void VisitDeclarations(ZoneList<Declaration*>* decls); |
void VisitStatements(ZoneList<Statement*>* stmts); |
@@ -75,9 +61,6 @@ |
bool has_supported_syntax_; |
- // The desired expression context of the currently visited expression. |
- Expression::Context context_; |
- |
DISALLOW_COPY_AND_ASSIGN(CodeGenSelector); |
}; |
@@ -649,12 +632,12 @@ |
void CodeGenSelector::VisitDeclaration(Declaration* decl) { |
Property* prop = decl->proxy()->AsProperty(); |
if (prop != NULL) { |
- ProcessExpression(prop->obj(), Expression::kValue); |
- ProcessExpression(prop->key(), Expression::kValue); |
+ Visit(prop->obj()); |
+ Visit(prop->key()); |
} |
if (decl->fun() != NULL) { |
- ProcessExpression(decl->fun(), Expression::kValue); |
+ Visit(decl->fun()); |
} |
} |
@@ -665,17 +648,15 @@ |
void CodeGenSelector::VisitExpressionStatement(ExpressionStatement* stmt) { |
- ProcessExpression(stmt->expression(), Expression::kEffect); |
+ Visit(stmt->expression()); |
} |
-void CodeGenSelector::VisitEmptyStatement(EmptyStatement* stmt) { |
- // EmptyStatement is supported. |
-} |
+void CodeGenSelector::VisitEmptyStatement(EmptyStatement* stmt) {} |
void CodeGenSelector::VisitIfStatement(IfStatement* stmt) { |
- ProcessExpression(stmt->condition(), Expression::kTest); |
+ Visit(stmt->condition()); |
CHECK_BAILOUT; |
Visit(stmt->then_statement()); |
CHECK_BAILOUT; |
@@ -683,27 +664,23 @@ |
} |
-void CodeGenSelector::VisitContinueStatement(ContinueStatement* stmt) { |
-} |
+void CodeGenSelector::VisitContinueStatement(ContinueStatement* stmt) {} |
-void CodeGenSelector::VisitBreakStatement(BreakStatement* stmt) { |
-} |
+void CodeGenSelector::VisitBreakStatement(BreakStatement* stmt) {} |
void CodeGenSelector::VisitReturnStatement(ReturnStatement* stmt) { |
- ProcessExpression(stmt->expression(), Expression::kValue); |
+ Visit(stmt->expression()); |
} |
void CodeGenSelector::VisitWithEnterStatement(WithEnterStatement* stmt) { |
- ProcessExpression(stmt->expression(), Expression::kValue); |
+ Visit(stmt->expression()); |
} |
-void CodeGenSelector::VisitWithExitStatement(WithExitStatement* stmt) { |
- // Supported. |
-} |
+void CodeGenSelector::VisitWithExitStatement(WithExitStatement* stmt) {} |
void CodeGenSelector::VisitSwitchStatement(SwitchStatement* stmt) { |
@@ -712,18 +689,14 @@ |
void CodeGenSelector::VisitDoWhileStatement(DoWhileStatement* stmt) { |
- // We do not handle loops with breaks or continue statements in their |
- // body. We will bailout when we hit those statements in the body. |
- ProcessExpression(stmt->cond(), Expression::kTest); |
+ Visit(stmt->cond()); |
CHECK_BAILOUT; |
Visit(stmt->body()); |
} |
void CodeGenSelector::VisitWhileStatement(WhileStatement* stmt) { |
- // We do not handle loops with breaks or continue statements in their |
- // body. We will bailout when we hit those statements in the body. |
- ProcessExpression(stmt->cond(), Expression::kTest); |
+ Visit(stmt->cond()); |
CHECK_BAILOUT; |
Visit(stmt->body()); |
} |
@@ -753,14 +726,10 @@ |
} |
-void CodeGenSelector::VisitDebuggerStatement(DebuggerStatement* stmt) { |
- // Debugger statement is supported. |
-} |
+void CodeGenSelector::VisitDebuggerStatement(DebuggerStatement* stmt) {} |
-void CodeGenSelector::VisitFunctionLiteral(FunctionLiteral* expr) { |
- // Function literal is supported. |
-} |
+void CodeGenSelector::VisitFunctionLiteral(FunctionLiteral* expr) {} |
void CodeGenSelector::VisitFunctionBoilerplateLiteral( |
@@ -770,11 +739,11 @@ |
void CodeGenSelector::VisitConditional(Conditional* expr) { |
- ProcessExpression(expr->condition(), Expression::kTest); |
+ Visit(expr->condition()); |
CHECK_BAILOUT; |
- ProcessExpression(expr->then_expression(), context_); |
+ Visit(expr->then_expression()); |
CHECK_BAILOUT; |
- ProcessExpression(expr->else_expression(), context_); |
+ Visit(expr->else_expression()); |
} |
@@ -784,11 +753,9 @@ |
void CodeGenSelector::VisitVariableProxy(VariableProxy* expr) { |
- Expression* rewrite = expr->var()->rewrite(); |
- // A rewrite of NULL indicates a global variable. |
- if (rewrite != NULL) { |
- // Non-global. |
- Slot* slot = rewrite->AsSlot(); |
+ Variable* var = expr->var(); |
+ if (!var->is_global()) { |
fschneider
2010/01/19 12:36:10
This is clearer than before and should be fine.
I
|
+ Slot* slot = var->slot(); |
if (slot != NULL) { |
Slot::Type type = slot->type(); |
// When LOOKUP slots are enabled, some currently dead code |
@@ -797,10 +764,10 @@ |
BAILOUT("Lookup slot"); |
} |
} else { |
+ // If not global or a slot, it is a parameter rewritten to an explicit |
+ // property reference on the (shadow) arguments object. |
#ifdef DEBUG |
- // Only remaining possibility is a property where the object is |
- // a slotted variable and the key is a smi. |
- Property* property = rewrite->AsProperty(); |
+ Property* property = var->AsProperty(); |
ASSERT_NOT_NULL(property); |
Variable* object = property->obj()->AsVariableProxy()->AsVariable(); |
ASSERT_NOT_NULL(object); |
@@ -813,14 +780,10 @@ |
} |
-void CodeGenSelector::VisitLiteral(Literal* expr) { |
- /* Nothing to do. */ |
-} |
+void CodeGenSelector::VisitLiteral(Literal* expr) {} |
-void CodeGenSelector::VisitRegExpLiteral(RegExpLiteral* expr) { |
- /* Nothing to do. */ |
-} |
+void CodeGenSelector::VisitRegExpLiteral(RegExpLiteral* expr) {} |
void CodeGenSelector::VisitObjectLiteral(ObjectLiteral* expr) { |
@@ -829,32 +792,10 @@ |
for (int i = 0, len = properties->length(); i < len; i++) { |
ObjectLiteral::Property* property = properties->at(i); |
if (property->IsCompileTimeValue()) continue; |
- |
- switch (property->kind()) { |
- case ObjectLiteral::Property::CONSTANT: |
- UNREACHABLE(); |
- |
- // For (non-compile-time) materialized literals and computed |
- // properties with symbolic keys we will use an IC and therefore not |
- // generate code for the key. |
- case ObjectLiteral::Property::COMPUTED: // Fall through. |
- case ObjectLiteral::Property::MATERIALIZED_LITERAL: |
- if (property->key()->handle()->IsSymbol()) { |
- break; |
- } |
- // Fall through. |
- |
- // In all other cases we need the key's value on the stack |
- // for a runtime call. (Relies on TEMP meaning STACK.) |
- case ObjectLiteral::Property::GETTER: // Fall through. |
- case ObjectLiteral::Property::SETTER: // Fall through. |
- case ObjectLiteral::Property::PROTOTYPE: |
- ProcessExpression(property->key(), Expression::kValue); |
- CHECK_BAILOUT; |
- break; |
- } |
- ProcessExpression(property->value(), Expression::kValue); |
+ Visit(property->key()); |
CHECK_BAILOUT; |
+ Visit(property->value()); |
+ CHECK_BAILOUT; |
} |
} |
@@ -865,16 +806,16 @@ |
Expression* subexpr = subexprs->at(i); |
if (subexpr->AsLiteral() != NULL) continue; |
if (CompileTimeValue::IsCompileTimeValue(subexpr)) continue; |
- ProcessExpression(subexpr, Expression::kValue); |
+ Visit(subexpr); |
CHECK_BAILOUT; |
} |
} |
void CodeGenSelector::VisitCatchExtensionObject(CatchExtensionObject* expr) { |
- ProcessExpression(expr->key(), Expression::kValue); |
+ Visit(expr->key()); |
CHECK_BAILOUT; |
- ProcessExpression(expr->value(), Expression::kValue); |
+ Visit(expr->value()); |
} |
@@ -900,33 +841,28 @@ |
} |
} |
} else if (prop != NULL) { |
- ProcessExpression(prop->obj(), Expression::kValue); |
+ Visit(prop->obj()); |
CHECK_BAILOUT; |
- // We will only visit the key during code generation for keyed property |
- // stores. Leave its expression context uninitialized for named |
- // property stores. |
- if (!prop->key()->IsPropertyName()) { |
- ProcessExpression(prop->key(), Expression::kValue); |
- CHECK_BAILOUT; |
- } |
+ Visit(prop->key()); |
+ CHECK_BAILOUT; |
} else { |
// This is a throw reference error. |
BAILOUT("non-variable/non-property assignment"); |
} |
- ProcessExpression(expr->value(), Expression::kValue); |
+ Visit(expr->value()); |
} |
void CodeGenSelector::VisitThrow(Throw* expr) { |
- ProcessExpression(expr->exception(), Expression::kValue); |
+ Visit(expr->exception()); |
} |
void CodeGenSelector::VisitProperty(Property* expr) { |
- ProcessExpression(expr->obj(), Expression::kValue); |
+ Visit(expr->obj()); |
CHECK_BAILOUT; |
- ProcessExpression(expr->key(), Expression::kValue); |
+ Visit(expr->key()); |
} |
@@ -946,34 +882,29 @@ |
} else if (fun->AsProperty() != NULL) { |
Property* prop = fun->AsProperty(); |
Literal* literal_key = prop->key()->AsLiteral(); |
- if (literal_key != NULL && literal_key->handle()->IsSymbol()) { |
- ProcessExpression(prop->obj(), Expression::kValue); |
- CHECK_BAILOUT; |
- } else { |
- ProcessExpression(prop->obj(), Expression::kValue); |
- CHECK_BAILOUT; |
- ProcessExpression(prop->key(), Expression::kValue); |
- CHECK_BAILOUT; |
- } |
+ Visit(prop->obj()); |
+ CHECK_BAILOUT; |
+ Visit(prop->key()); |
+ CHECK_BAILOUT; |
} else { |
// Otherwise the call is supported if the function expression is. |
- ProcessExpression(fun, Expression::kValue); |
+ Visit(fun); |
} |
// Check all arguments to the call. |
for (int i = 0; i < args->length(); i++) { |
- ProcessExpression(args->at(i), Expression::kValue); |
+ Visit(args->at(i)); |
CHECK_BAILOUT; |
} |
} |
void CodeGenSelector::VisitCallNew(CallNew* expr) { |
- ProcessExpression(expr->expression(), Expression::kValue); |
+ Visit(expr->expression()); |
CHECK_BAILOUT; |
ZoneList<Expression*>* args = expr->arguments(); |
// Check all arguments to the call |
for (int i = 0; i < args->length(); i++) { |
- ProcessExpression(args->at(i), Expression::kValue); |
+ Visit(args->at(i)); |
CHECK_BAILOUT; |
} |
} |
@@ -987,7 +918,7 @@ |
} |
// Check all arguments to the call. (Relies on TEMP meaning STACK.) |
for (int i = 0; i < expr->arguments()->length(); i++) { |
- ProcessExpression(expr->arguments()->at(i), Expression::kValue); |
+ Visit(expr->arguments()->at(i)); |
CHECK_BAILOUT; |
} |
} |
@@ -996,16 +927,16 @@ |
void CodeGenSelector::VisitUnaryOperation(UnaryOperation* expr) { |
switch (expr->op()) { |
case Token::VOID: |
- ProcessExpression(expr->expression(), Expression::kEffect); |
- break; |
case Token::NOT: |
- ProcessExpression(expr->expression(), Expression::kTest); |
- break; |
case Token::TYPEOF: |
- ProcessExpression(expr->expression(), Expression::kValue); |
+ Visit(expr->expression()); |
break; |
+ case BIT_NOT: |
+ BAILOUT("UnaryOperataion: BIT_NOT"); |
+ case DELETE: |
+ BAILOUT("UnaryOperataion: DELETE"); |
default: |
- BAILOUT("UnaryOperation"); |
+ UNREACHABLE(); |
} |
} |
@@ -1024,15 +955,10 @@ |
} |
} |
} else if (prop != NULL) { |
- ProcessExpression(prop->obj(), Expression::kValue); |
+ Visit(prop->obj()); |
CHECK_BAILOUT; |
- // We will only visit the key during code generation for keyed property |
- // stores. Leave its expression context uninitialized for named |
- // property stores. |
- if (!prop->key()->IsPropertyName()) { |
- ProcessExpression(prop->key(), Expression::kValue); |
- CHECK_BAILOUT; |
- } |
+ Visit(prop->key()); |
+ CHECK_BAILOUT; |
} else { |
// This is a throw reference error. |
BAILOUT("CountOperation non-variable/non-property expression"); |
@@ -1041,89 +967,20 @@ |
void CodeGenSelector::VisitBinaryOperation(BinaryOperation* expr) { |
- switch (expr->op()) { |
- case Token::COMMA: |
- ProcessExpression(expr->left(), Expression::kEffect); |
- CHECK_BAILOUT; |
- ProcessExpression(expr->right(), context_); |
- break; |
- |
- case Token::OR: |
- switch (context_) { |
- case Expression::kUninitialized: |
- UNREACHABLE(); |
- case Expression::kEffect: // Fall through. |
- case Expression::kTest: // Fall through. |
- case Expression::kTestValue: |
- // The left subexpression's value is not needed, it is in a pure |
- // test context. |
- ProcessExpression(expr->left(), Expression::kTest); |
- break; |
- case Expression::kValue: // Fall through. |
- case Expression::kValueTest: |
- // The left subexpression's value is needed, it is in a hybrid |
- // value/test context. |
- ProcessExpression(expr->left(), Expression::kValueTest); |
- break; |
- } |
- CHECK_BAILOUT; |
- ProcessExpression(expr->right(), context_); |
- break; |
- |
- case Token::AND: |
- switch (context_) { |
- case Expression::kUninitialized: |
- UNREACHABLE(); |
- case Expression::kEffect: // Fall through. |
- case Expression::kTest: // Fall through. |
- case Expression::kValueTest: |
- // The left subexpression's value is not needed, it is in a pure |
- // test context. |
- ProcessExpression(expr->left(), Expression::kTest); |
- break; |
- case Expression::kValue: // Fall through. |
- case Expression::kTestValue: |
- // The left subexpression's value is needed, it is in a hybrid |
- // test/value context. |
- ProcessExpression(expr->left(), Expression::kTestValue); |
- break; |
- } |
- CHECK_BAILOUT; |
- ProcessExpression(expr->right(), context_); |
- break; |
- |
- case Token::ADD: |
- case Token::SUB: |
- case Token::DIV: |
- case Token::MOD: |
- case Token::MUL: |
- case Token::BIT_OR: |
- case Token::BIT_AND: |
- case Token::BIT_XOR: |
- case Token::SHL: |
- case Token::SHR: |
- case Token::SAR: |
- ProcessExpression(expr->left(), Expression::kValue); |
- CHECK_BAILOUT; |
- ProcessExpression(expr->right(), Expression::kValue); |
- break; |
- |
- default: |
- BAILOUT("Unsupported binary operation"); |
- } |
+ Visit(expr->left()); |
+ CHECK_BAILOUT; |
+ Visit(expr->right()); |
} |
void CodeGenSelector::VisitCompareOperation(CompareOperation* expr) { |
- ProcessExpression(expr->left(), Expression::kValue); |
+ Visit(expr->left()); |
CHECK_BAILOUT; |
- ProcessExpression(expr->right(), Expression::kValue); |
+ Visit(expr->right()); |
} |
-void CodeGenSelector::VisitThisFunction(ThisFunction* expr) { |
- // ThisFunction is supported. |
-} |
+void CodeGenSelector::VisitThisFunction(ThisFunction* expr) {} |
#undef BAILOUT |
#undef CHECK_BAILOUT |