OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #if V8_TARGET_ARCH_ARM64 | 5 #if V8_TARGET_ARCH_ARM64 |
6 | 6 |
7 #include "src/full-codegen/full-codegen.h" | 7 #include "src/full-codegen/full-codegen.h" |
8 #include "src/ast/compile-time-value.h" | 8 #include "src/ast/compile-time-value.h" |
9 #include "src/ast/scopes.h" | 9 #include "src/ast/scopes.h" |
10 #include "src/code-factory.h" | 10 #include "src/code-factory.h" |
(...skipping 3360 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3371 __ Ldrb(x1, FieldMemOperand(x0, Map::kBitFieldOffset)); | 3371 __ Ldrb(x1, FieldMemOperand(x0, Map::kBitFieldOffset)); |
3372 __ TestAndSplit(x1, 1 << Map::kIsUndetectable, if_false, if_true, | 3372 __ TestAndSplit(x1, 1 << Map::kIsUndetectable, if_false, if_true, |
3373 fall_through); | 3373 fall_through); |
3374 } | 3374 } |
3375 | 3375 |
3376 context()->Plug(if_true, if_false); | 3376 context()->Plug(if_true, if_false); |
3377 } | 3377 } |
3378 | 3378 |
3379 | 3379 |
3380 void FullCodeGenerator::VisitYield(Yield* expr) { | 3380 void FullCodeGenerator::VisitYield(Yield* expr) { |
3381 Comment cmnt(masm_, "[ Yield"); | 3381 // Resumable functions are not supported. |
3382 SetExpressionPosition(expr); | 3382 UNREACHABLE(); |
3383 | |
3384 // Evaluate yielded value first; the initial iterator definition depends on | |
3385 // this. It stays on the stack while we update the iterator. | |
3386 VisitForStackValue(expr->expression()); | |
3387 | |
3388 // TODO(jbramley): Tidy this up once the merge is done, using named registers | |
3389 // and suchlike. The implementation changes a little by bleeding_edge so I | |
3390 // don't want to spend too much time on it now. | |
3391 | |
3392 Label suspend, continuation, post_runtime, resume, exception; | |
3393 | |
3394 __ B(&suspend); | |
3395 // TODO(jbramley): This label is bound here because the following code | |
3396 // looks at its pos(). Is it possible to do something more efficient here, | |
3397 // perhaps using Adr? | |
3398 __ Bind(&continuation); | |
3399 // When we arrive here, x0 holds the generator object. | |
3400 __ RecordGeneratorContinuation(); | |
3401 __ Ldr(x1, FieldMemOperand(x0, JSGeneratorObject::kResumeModeOffset)); | |
3402 __ Ldr(x0, FieldMemOperand(x0, JSGeneratorObject::kInputOrDebugPosOffset)); | |
3403 STATIC_ASSERT(JSGeneratorObject::kNext < JSGeneratorObject::kReturn); | |
3404 STATIC_ASSERT(JSGeneratorObject::kThrow > JSGeneratorObject::kReturn); | |
3405 __ Cmp(x1, Operand(Smi::FromInt(JSGeneratorObject::kReturn))); | |
3406 __ B(lt, &resume); | |
3407 __ Push(result_register()); | |
3408 __ B(gt, &exception); | |
3409 EmitCreateIteratorResult(true); | |
3410 EmitUnwindAndReturn(); | |
3411 | |
3412 __ Bind(&exception); | |
3413 __ CallRuntime(expr->rethrow_on_exception() ? Runtime::kReThrow | |
3414 : Runtime::kThrow); | |
3415 | |
3416 __ Bind(&suspend); | |
3417 OperandStackDepthIncrement(1); // Not popped on this path. | |
3418 VisitForAccumulatorValue(expr->generator_object()); | |
3419 DCHECK((continuation.pos() > 0) && Smi::IsValid(continuation.pos())); | |
3420 __ Mov(x1, Smi::FromInt(continuation.pos())); | |
3421 __ Str(x1, FieldMemOperand(x0, JSGeneratorObject::kContinuationOffset)); | |
3422 __ Str(cp, FieldMemOperand(x0, JSGeneratorObject::kContextOffset)); | |
3423 __ Mov(x1, cp); | |
3424 __ RecordWriteField(x0, JSGeneratorObject::kContextOffset, x1, x2, | |
3425 kLRHasBeenSaved, kDontSaveFPRegs); | |
3426 __ Add(x1, fp, StandardFrameConstants::kExpressionsOffset); | |
3427 __ Cmp(__ StackPointer(), x1); | |
3428 __ B(eq, &post_runtime); | |
3429 __ Push(x0); // generator object | |
3430 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); | |
3431 RestoreContext(); | |
3432 __ Bind(&post_runtime); | |
3433 PopOperand(result_register()); | |
3434 EmitReturnSequence(); | |
3435 | |
3436 __ Bind(&resume); | |
3437 context()->Plug(result_register()); | |
3438 } | 3383 } |
3439 | 3384 |
3440 void FullCodeGenerator::PushOperands(Register reg1, Register reg2) { | 3385 void FullCodeGenerator::PushOperands(Register reg1, Register reg2) { |
3441 OperandStackDepthIncrement(2); | 3386 OperandStackDepthIncrement(2); |
3442 __ Push(reg1, reg2); | 3387 __ Push(reg1, reg2); |
3443 } | 3388 } |
3444 | 3389 |
3445 void FullCodeGenerator::PushOperands(Register reg1, Register reg2, | 3390 void FullCodeGenerator::PushOperands(Register reg1, Register reg2, |
3446 Register reg3) { | 3391 Register reg3) { |
3447 OperandStackDepthIncrement(3); | 3392 OperandStackDepthIncrement(3); |
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3701 } | 3646 } |
3702 | 3647 |
3703 return INTERRUPT; | 3648 return INTERRUPT; |
3704 } | 3649 } |
3705 | 3650 |
3706 | 3651 |
3707 } // namespace internal | 3652 } // namespace internal |
3708 } // namespace v8 | 3653 } // namespace v8 |
3709 | 3654 |
3710 #endif // V8_TARGET_ARCH_ARM64 | 3655 #endif // V8_TARGET_ARCH_ARM64 |
OLD | NEW |