Index: src/full-codegen/arm64/full-codegen-arm64.cc |
diff --git a/src/full-codegen/arm64/full-codegen-arm64.cc b/src/full-codegen/arm64/full-codegen-arm64.cc |
index 3ebd627b93d2aca976e81e5630a406df8c02d170..a9482046d85489a1faa3206954b9f48992db5047 100644 |
--- a/src/full-codegen/arm64/full-codegen-arm64.cc |
+++ b/src/full-codegen/arm64/full-codegen-arm64.cc |
@@ -4355,8 +4355,17 @@ void FullCodeGenerator::VisitYield(Yield* expr) { |
// looks at its pos(). Is it possible to do something more efficient here, |
// perhaps using Adr? |
__ Bind(&continuation); |
+ // When we arrive here, the stack top is the resume mode and |
+ // result_register() holds the input value (the argument given to the |
+ // respective resume operation). |
__ RecordGeneratorContinuation(); |
- __ B(&resume); |
+ __ Pop(x1); |
+ __ Cmp(x1, Smi::FromInt(JSGeneratorObject::RETURN)); |
+ __ B(ne, &resume); |
+ __ Push(result_register()); |
+ EmitCreateIteratorResult(true); |
+ EmitUnwindBeforeReturn(); |
+ EmitReturnSequence(); |
__ Bind(&suspend); |
VisitForAccumulatorValue(expr->generator_object()); |
@@ -4384,9 +4393,6 @@ void FullCodeGenerator::VisitYield(Yield* expr) { |
case Yield::kFinal: { |
VisitForAccumulatorValue(expr->generator_object()); |
- __ Mov(x1, Smi::FromInt(JSGeneratorObject::kGeneratorClosed)); |
- __ Str(x1, FieldMemOperand(result_register(), |
- JSGeneratorObject::kContinuationOffset)); |
// Pop value from top-of-stack slot, box result into result register. |
EmitCreateIteratorResult(true); |
EmitUnwindBeforeReturn(); |
@@ -4433,6 +4439,10 @@ void FullCodeGenerator::VisitYield(Yield* expr) { |
// perhaps using Adr? |
__ Bind(&l_continuation); |
__ RecordGeneratorContinuation(); |
+ __ pop(x1); |
+ // TODO(neis): Ignoring the resume mode here is clearly wrong. Currently, |
+ // return is not supported for yield*. The planned desugaring of yield* |
+ // using do-expressions will naturally solve this. |
__ B(&l_resume); |
__ Bind(&l_suspend); |
@@ -4580,6 +4590,7 @@ void FullCodeGenerator::EmitGeneratorResume(Expression *generator, |
__ Mov(x12, Smi::FromInt(JSGeneratorObject::kGeneratorExecuting)); |
__ Str(x12, FieldMemOperand(generator_object, |
JSGeneratorObject::kContinuationOffset)); |
+ __ Push(Smi::FromInt(resume_mode)); // Consumed in continuation. |
__ Br(x10); |
__ Bind(&slow_resume); |
@@ -4590,6 +4601,7 @@ void FullCodeGenerator::EmitGeneratorResume(Expression *generator, |
__ PushMultipleTimes(the_hole, operand_stack_size); |
__ Mov(x10, Smi::FromInt(resume_mode)); |
+ __ Push(Smi::FromInt(resume_mode)); // Consumed in continuation. |
__ Push(generator_object, result_register(), x10); |
__ CallRuntime(Runtime::kResumeJSGeneratorObject); |
// Not reached: the runtime call returns elsewhere. |