Index: src/arm/fast-codegen-arm.cc |
=================================================================== |
--- src/arm/fast-codegen-arm.cc (revision 3133) |
+++ src/arm/fast-codegen-arm.cc (working copy) |
@@ -149,22 +149,16 @@ |
Comment cmnt(masm_, "[ ReturnStatement"); |
SetStatementPosition(stmt); |
Expression* expr = stmt->expression(); |
- Visit(expr); |
- |
- // Complete the statement based on the location of the subexpression. |
- Location source = expr->location(); |
- ASSERT(!source.is_nowhere()); |
- if (source.is_temporary()) { |
- __ pop(r0); |
- } else { |
- ASSERT(source.is_constant()); |
- ASSERT(expr->AsLiteral() != NULL); |
+ // Complete the statement based on the type of the subexpression. |
+ if (expr->AsLiteral() != NULL) { |
__ mov(r0, Operand(expr->AsLiteral()->handle())); |
+ } else { |
+ Visit(expr); |
+ ASSERT(expr->location().is_temporary()); |
+ __ pop(r0); |
} |
if (FLAG_trace) { |
- // Push the return value on the stack as the parameter. |
- // Runtime::TraceExit returns its parameter in r0. |
__ push(r0); |
__ CallRuntime(Runtime::kTraceExit, 1); |
} |
@@ -234,6 +228,16 @@ |
} |
+void FastCodeGenerator::VisitLiteral(Literal* expr) { |
+ if (expr->location().is_temporary()) { |
+ __ mov(ip, Operand(expr->AsLiteral()->handle())); |
+ __ push(ip); |
+ } else { |
+ ASSERT(expr->location().is_nowhere()); |
+ } |
+} |
+ |
+ |
void FastCodeGenerator::VisitObjectLiteral(ObjectLiteral* expr) { |
Comment cmnt(masm_, "[ ObjectLiteral"); |
Label boilerplate_exists; |
@@ -288,10 +292,7 @@ |
case ObjectLiteral::Property::PROTOTYPE: |
__ push(r0); |
Visit(key); |
- if (key->location().is_constant()) { |
- __ mov(r1, Operand(key->handle())); |
- __ push(r1); |
- } |
+ ASSERT(key->location().is_temporary()); |
Visit(value); |
ASSERT(value->location().is_temporary()); |
__ CallRuntime(Runtime::kSetProperty, 3); |
@@ -301,10 +302,7 @@ |
case ObjectLiteral::Property::GETTER: |
__ push(r0); |
Visit(key); |
- if (key->location().is_constant()) { |
- __ mov(r1, Operand(key->handle())); |
- __ push(r1); |
- } |
+ ASSERT(key->location().is_temporary()); |
__ mov(r1, Operand(property->kind() == ObjectLiteral::Property::SETTER ? |
Smi::FromInt(1) : |
Smi::FromInt(0))); |
@@ -433,31 +431,26 @@ |
void FastCodeGenerator::VisitAssignment(Assignment* expr) { |
Comment cmnt(masm_, "[ Assignment"); |
ASSERT(expr->op() == Token::ASSIGN || expr->op() == Token::INIT_VAR); |
- Expression* rhs = expr->value(); |
- Visit(rhs); |
// Left-hand side can only be a global or a (parameter or local) slot. |
Variable* var = expr->target()->AsVariableProxy()->AsVariable(); |
ASSERT(var != NULL); |
ASSERT(var->is_global() || var->slot() != NULL); |
- // Complete the assignment based on the location of the right-hand-side |
- // value and the desired location of the assignment value. |
+ Expression* rhs = expr->value(); |
Location destination = expr->location(); |
- Location source = rhs->location(); |
- ASSERT(!destination.is_constant()); |
- ASSERT(!source.is_nowhere()); |
- |
if (var->is_global()) { |
// Assignment to a global variable, use inline caching. Right-hand-side |
// value is passed in r0, variable name in r2, and the global object on |
// the stack. |
- if (source.is_temporary()) { |
- __ pop(r0); |
- } else { |
- ASSERT(source.is_constant()); |
- ASSERT(rhs->AsLiteral() != NULL); |
+ |
+ // Code for the right-hand-side expression depends on its type. |
+ if (rhs->AsLiteral() != NULL) { |
__ mov(r0, Operand(rhs->AsLiteral()->handle())); |
+ } else { |
+ ASSERT(rhs->location().is_temporary()); |
+ Visit(rhs); |
+ __ pop(r0); |
} |
__ mov(r2, Operand(var->name())); |
__ ldr(ip, CodeGenerator::GlobalObject()); |
@@ -473,8 +466,22 @@ |
} |
} else { |
- if (source.is_temporary()) { |
+ // Local or parameter assignment. |
+ |
+ // Code for the right-hand side expression depends on its type. |
+ if (rhs->AsLiteral() != NULL) { |
+ // Two cases: 'temp <- (var = constant)', or 'var = constant' with a |
+ // discarded result. Always perform the assignment. |
+ __ mov(ip, Operand(rhs->AsLiteral()->handle())); |
+ __ str(ip, MemOperand(fp, SlotOffset(var->slot()))); |
if (destination.is_temporary()) { |
+ // Case 'temp <- (var = constant)'. Save result. |
+ __ push(ip); |
+ } |
fschneider
2009/10/26 17:57:20
Add an assert here to be consistent with the rest
|
+ } else { |
+ ASSERT(rhs->location().is_temporary()); |
+ Visit(rhs); |
+ if (destination.is_temporary()) { |
// Case 'temp1 <- (var = temp0)'. Preserve right-hand-side |
// temporary on the stack. |
__ ldr(ip, MemOperand(sp)); |
@@ -484,17 +491,6 @@ |
__ pop(ip); |
} |
__ str(ip, MemOperand(fp, SlotOffset(var->slot()))); |
- } else { |
- ASSERT(source.is_constant()); |
- ASSERT(rhs->AsLiteral() != NULL); |
- // Two cases: 'temp <- (var = constant)', or 'var = constant' with a |
- // discarded result. Always perform the assignment. |
- __ mov(ip, Operand(rhs->AsLiteral()->handle())); |
- __ str(ip, MemOperand(fp, SlotOffset(var->slot()))); |
- if (destination.is_temporary()) { |
- // Case 'temp <- (var = constant)'. Save result. |
- __ push(ip); |
- } |
} |
} |
} |
@@ -515,12 +511,7 @@ |
int arg_count = args->length(); |
for (int i = 0; i < arg_count; i++) { |
Visit(args->at(i)); |
- ASSERT(!args->at(i)->location().is_nowhere()); |
- if (args->at(i)->location().is_constant()) { |
- ASSERT(args->at(i)->AsLiteral() != NULL); |
- __ mov(r0, Operand(args->at(i)->AsLiteral()->handle())); |
- __ push(r0); |
- } |
+ ASSERT(args->at(i)->location().is_temporary()); |
} |
// Record source position for debugger |
SetSourcePosition(expr->position()); |
@@ -550,16 +541,7 @@ |
int arg_count = args->length(); |
for (int i = 0; i < arg_count; i++) { |
Visit(args->at(i)); |
- ASSERT(!args->at(i)->location().is_nowhere()); |
- if (args->at(i)->location().is_constant()) { |
- ASSERT(args->at(i)->AsLiteral() != NULL); |
- __ mov(r0, Operand(args->at(i)->AsLiteral()->handle())); |
- __ push(r0); |
- } else { |
- ASSERT(args->at(i)->location().is_temporary()); |
- // If location is temporary, it is already on the stack, |
- // so nothing to do here. |
- } |
+ ASSERT(args->at(i)->location().is_temporary()); |
} |
__ CallRuntime(function, arg_count); |
@@ -580,30 +562,23 @@ |
Label done; |
Location destination = expr->location(); |
- ASSERT(!destination.is_constant()); |
- |
Expression* left = expr->left(); |
- Location left_source = left->location(); |
- ASSERT(!left_source.is_nowhere()); |
- |
Expression* right = expr->right(); |
- Location right_source = right->location(); |
- ASSERT(!right_source.is_nowhere()); |
- Visit(left); |
// Call the runtime to find the boolean value of the left-hand |
// subexpression. Duplicate the value if it may be needed as the final |
// result. |
- if (left_source.is_temporary()) { |
+ if (left->AsLiteral() != NULL) { |
+ __ mov(r0, Operand(left->AsLiteral()->handle())); |
+ __ push(r0); |
+ if (destination.is_temporary()) __ push(r0); |
fschneider
2009/10/26 17:57:20
May want to add an assert here to be consistent wi
|
+ } else { |
+ Visit(left); |
+ ASSERT(left->location().is_temporary()); |
if (destination.is_temporary()) { |
__ ldr(r0, MemOperand(sp)); |
__ push(r0); |
} |
fschneider
2009/10/26 17:57:20
Add an assert:
else {
ASSERT(destination.is_now
|
- } else { |
- ASSERT(left->AsLiteral() != NULL); |
- __ mov(r0, Operand(left->AsLiteral()->handle())); |
- __ push(r0); |
- if (destination.is_temporary()) __ push(r0); |
} |
// The left-hand value is in on top of the stack. It is duplicated on the |
// stack iff the destination location is temporary. |
@@ -614,15 +589,22 @@ |
// Discard the left-hand value if present on the stack. |
if (destination.is_temporary()) __ pop(); |
- Visit(right); |
- |
// Save or discard the right-hand value as needed. |
- if (destination.is_temporary() && right_source.is_constant()) { |
- ASSERT(right->AsLiteral() != NULL); |
- __ mov(ip, Operand(right->AsLiteral()->handle())); |
- __ push(ip); |
- } else if (destination.is_nowhere() && right_source.is_temporary()) { |
- __ pop(); |
+ if (right->AsLiteral() != NULL) { |
+ if (destination.is_temporary()) { |
+ __ mov(ip, Operand(right->AsLiteral()->handle())); |
+ __ push(ip); |
+ } else { |
+ ASSERT(destination.is_nowhere()); |
+ } |
+ } else { |
+ Visit(right); |
+ ASSERT(right->location().is_temporary()); |
+ if (destination.is_nowhere()) { |
+ __ pop(); |
+ } else { |
+ ASSERT(destination.is_temporary()); |
+ } |
} |
__ bind(&done); |