Chromium Code Reviews| Index: src/interpreter/bytecode-generator.cc |
| diff --git a/src/interpreter/bytecode-generator.cc b/src/interpreter/bytecode-generator.cc |
| index 6fbb46e722bc3c67896e1e2a9d059747d830f4d8..851ad61cc4fa3e13f49b514d7aa47b73eb71ae54 100644 |
| --- a/src/interpreter/bytecode-generator.cc |
| +++ b/src/interpreter/bytecode-generator.cc |
| @@ -654,6 +654,25 @@ void BytecodeGenerator::VisitProperty(Property* expr) { |
| } |
| +Register BytecodeGenerator::VisitArguments( |
| + ZoneList<Expression*>* args, TemporaryRegisterScope* register_scope) { |
| + // Visit arguments and place in a contiguous block of temporary registers. |
| + // Return the first temporary register corresponding to the first argument. |
| + DCHECK_GT(args->length(), 0); |
| + Register first_arg = register_scope->NewRegister(); |
| + Visit(args->at(0)); |
| + builder()->StoreAccumulatorInRegister(first_arg); |
| + for (int i = 1; i < static_cast<int>(args->length()); i++) { |
| + Register ith_arg = register_scope->NewRegister(); |
| + Visit(args->at(i)); |
| + builder()->StoreAccumulatorInRegister(ith_arg); |
| + DCHECK(ith_arg.index() - i == first_arg.index()); |
| + } |
| + |
| + return first_arg; |
| +} |
| + |
| + |
| void BytecodeGenerator::VisitCall(Call* expr) { |
| Expression* callee_expr = expr->expression(); |
| Call::CallType call_type = expr->GetCallType(isolate()); |
| @@ -701,11 +720,9 @@ void BytecodeGenerator::VisitCall(Call* expr) { |
| // Evaluate all arguments to the function call and store in sequential |
| // registers. |
| ZoneList<Expression*>* args = expr->arguments(); |
| - for (int i = 0; i < args->length(); ++i) { |
| - Visit(args->at(i)); |
| - Register arg = temporary_register_scope.NewRegister(); |
| - DCHECK(arg.index() - i == receiver.index() + 1); |
| - builder()->StoreAccumulatorInRegister(arg); |
| + if (args->length() > 0) { |
| + Register first_arg = VisitArguments(args, &temporary_register_scope); |
| + CHECK_EQ(first_arg.index(), receiver.index() + 1); |
| } |
| // TODO(rmcilroy): Deal with possible direct eval here? |
| @@ -714,7 +731,19 @@ void BytecodeGenerator::VisitCall(Call* expr) { |
| } |
| -void BytecodeGenerator::VisitCallNew(CallNew* expr) { UNIMPLEMENTED(); } |
| +void BytecodeGenerator::VisitCallNew(CallNew* expr) { |
| + TemporaryRegisterScope temporary_register_scope(builder()); |
| + Register constructor = temporary_register_scope.NewRegister(); |
| + Visit(expr->expression()); |
| + builder()->StoreAccumulatorInRegister(constructor); |
| + ZoneList<Expression*>* args = expr->arguments(); |
| + if (args->length() > 0) { |
| + Register first_arg = VisitArguments(args, &temporary_register_scope); |
| + builder()->New(constructor, first_arg, args->length()); |
| + } else { |
| + builder()->New(constructor, constructor, 0); |
|
rmcilroy
2015/10/14 10:18:34
nit - I think it deserves a comment that you are p
oth
2015/10/14 16:02:19
Done.
|
| + } |
| +} |
| void BytecodeGenerator::VisitCallRuntime(CallRuntime* expr) { |
| @@ -723,22 +752,18 @@ void BytecodeGenerator::VisitCallRuntime(CallRuntime* expr) { |
| } |
| // Evaluate all arguments to the runtime call. |
| - ZoneList<Expression*>* args = expr->arguments(); |
| TemporaryRegisterScope temporary_register_scope(&builder_); |
| - // Ensure we always have a valid first_arg register even if there are no |
| - // arguments to pass. |
| - Register first_arg = temporary_register_scope.NewRegister(); |
| - for (int i = 0; i < args->length(); ++i) { |
| - Register arg = |
| - (i == 0) ? first_arg : temporary_register_scope.NewRegister(); |
| - Visit(args->at(i)); |
| - DCHECK_EQ(arg.index() - i, first_arg.index()); |
| - builder()->StoreAccumulatorInRegister(arg); |
| - } |
| // TODO(rmcilroy): support multiple return values. |
| DCHECK_LE(expr->function()->result_size, 1); |
| Runtime::FunctionId function_id = expr->function()->function_id; |
| + ZoneList<Expression*>* args = expr->arguments(); |
| + Register first_arg; |
| + if (args->length() > 0) { |
| + first_arg = VisitArguments(args, &temporary_register_scope); |
| + } else { |
| + first_arg = temporary_register_scope.NewRegister(); |
|
rmcilroy
2015/10/14 10:18:34
ditto
oth
2015/10/14 16:02:19
Done.
|
| + } |
| builder()->CallRuntime(function_id, first_arg, args->length()); |
| } |