| OLD | NEW |
| 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/globals.h" | 5 #include "vm/globals.h" |
| 6 #if defined(TARGET_ARCH_ARM64) | 6 #if defined(TARGET_ARCH_ARM64) |
| 7 | 7 |
| 8 #include "vm/assembler.h" | 8 #include "vm/assembler.h" |
| 9 #include "vm/code_generator.h" | 9 #include "vm/code_generator.h" |
| 10 #include "vm/compiler.h" | 10 #include "vm/compiler.h" |
| (...skipping 385 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 396 void StubCode::GenerateCallNoSuchMethodFunctionStub(Assembler* assembler) { | 396 void StubCode::GenerateCallNoSuchMethodFunctionStub(Assembler* assembler) { |
| 397 __ Stop("GenerateCallNoSuchMethodFunctionStub"); | 397 __ Stop("GenerateCallNoSuchMethodFunctionStub"); |
| 398 } | 398 } |
| 399 | 399 |
| 400 | 400 |
| 401 void StubCode::GenerateOptimizedUsageCounterIncrement(Assembler* assembler) { | 401 void StubCode::GenerateOptimizedUsageCounterIncrement(Assembler* assembler) { |
| 402 __ Stop("GenerateOptimizedUsageCounterIncrement"); | 402 __ Stop("GenerateOptimizedUsageCounterIncrement"); |
| 403 } | 403 } |
| 404 | 404 |
| 405 | 405 |
| 406 // Loads function into 'temp_reg'. |
| 406 void StubCode::GenerateUsageCounterIncrement(Assembler* assembler, | 407 void StubCode::GenerateUsageCounterIncrement(Assembler* assembler, |
| 407 Register temp_reg) { | 408 Register temp_reg) { |
| 408 __ Stop("GenerateUsageCounterIncrement"); | 409 Register ic_reg = R5; |
| 410 Register func_reg = temp_reg; |
| 411 ASSERT(temp_reg == R6); |
| 412 __ LoadFieldFromOffset(func_reg, ic_reg, ICData::function_offset()); |
| 413 __ LoadFieldFromOffset(R7, func_reg, Function::usage_counter_offset()); |
| 414 __ AddImmediate(R7, R7, 1, PP); |
| 415 __ StoreFieldToOffset(R7, func_reg, Function::usage_counter_offset()); |
| 409 } | 416 } |
| 410 | 417 |
| 411 | 418 |
| 412 void StubCode::GenerateNArgsCheckInlineCacheStub( | 419 void StubCode::GenerateNArgsCheckInlineCacheStub( |
| 413 Assembler* assembler, | 420 Assembler* assembler, |
| 414 intptr_t num_args, | 421 intptr_t num_args, |
| 415 const RuntimeEntry& handle_ic_miss) { | 422 const RuntimeEntry& handle_ic_miss) { |
| 416 __ Stop("GenerateNArgsCheckInlineCacheStub"); | 423 __ Stop("GenerateNArgsCheckInlineCacheStub"); |
| 417 } | 424 } |
| 418 | 425 |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 454 __ Stop("GenerateClosureCallInlineCacheStub"); | 461 __ Stop("GenerateClosureCallInlineCacheStub"); |
| 455 } | 462 } |
| 456 | 463 |
| 457 | 464 |
| 458 void StubCode::GenerateMegamorphicCallStub(Assembler* assembler) { | 465 void StubCode::GenerateMegamorphicCallStub(Assembler* assembler) { |
| 459 __ Stop("GenerateMegamorphicCallStub"); | 466 __ Stop("GenerateMegamorphicCallStub"); |
| 460 } | 467 } |
| 461 | 468 |
| 462 | 469 |
| 463 void StubCode::GenerateZeroArgsUnoptimizedStaticCallStub(Assembler* assembler) { | 470 void StubCode::GenerateZeroArgsUnoptimizedStaticCallStub(Assembler* assembler) { |
| 464 __ Stop("GenerateZeroArgsUnoptimizedStaticCallStub"); | 471 GenerateUsageCounterIncrement(assembler, R6); |
| 472 #if defined(DEBUG) |
| 473 { Label ok; |
| 474 // Check that the IC data array has NumberOfArgumentsChecked() == 0. |
| 475 // 'num_args_tested' is stored as an untagged int. |
| 476 __ LoadFieldFromOffset(R6, R5, ICData::num_args_tested_offset()); |
| 477 __ CompareImmediate(R6, 0, PP); |
| 478 __ b(&ok, EQ); |
| 479 __ Stop("Incorrect IC data for unoptimized static call"); |
| 480 __ Bind(&ok); |
| 481 } |
| 482 #endif // DEBUG |
| 483 |
| 484 // Check single stepping. |
| 485 Label not_stepping; |
| 486 __ LoadFieldFromOffset(R6, CTX, Context::isolate_offset()); |
| 487 __ LoadFromOffset(R6, R6, Isolate::single_step_offset(), kUnsignedByte); |
| 488 __ CompareImmediate(R6, 0, PP); |
| 489 __ b(¬_stepping, EQ); |
| 490 __ EnterStubFrame(); |
| 491 __ Push(R5); // Preserve IC data. |
| 492 __ CallRuntime(kSingleStepHandlerRuntimeEntry, 0); |
| 493 __ Pop(R5); |
| 494 __ LeaveStubFrame(); |
| 495 __ Bind(¬_stepping); |
| 496 |
| 497 // R5: IC data object (preserved). |
| 498 __ LoadFieldFromOffset(R6, R5, ICData::ic_data_offset()); |
| 499 // R6: ic_data_array with entries: target functions and count. |
| 500 __ AddImmediate(R6, R6, Array::data_offset() - kHeapObjectTag, PP); |
| 501 // R6: points directly to the first ic data array element. |
| 502 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize; |
| 503 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize; |
| 504 |
| 505 // Increment count for this call. |
| 506 Label increment_done; |
| 507 __ LoadFromOffset(R1, R6, count_offset); |
| 508 __ adds(R1, R1, Operand(Smi::RawValue(1))); |
| 509 __ StoreToOffset(R1, R6, count_offset); |
| 510 __ b(&increment_done, VC); // No overflow. |
| 511 __ LoadImmediate(R1, Smi::RawValue(Smi::kMaxValue), PP); |
| 512 __ StoreToOffset(R1, R6, count_offset); |
| 513 __ Bind(&increment_done); |
| 514 |
| 515 // Load arguments descriptor into R4. |
| 516 __ LoadFieldFromOffset(R4, R5, ICData::arguments_descriptor_offset()); |
| 517 |
| 518 // Get function and call it, if possible. |
| 519 __ LoadFromOffset(R0, R6, target_offset); |
| 520 __ LoadFieldFromOffset(R2, R0, Function::code_offset()); |
| 521 |
| 522 // R0: function. |
| 523 // R2: target code. |
| 524 __ LoadFieldFromOffset(R2, R2, Code::instructions_offset()); |
| 525 __ AddImmediate(R2, R2, Instructions::HeaderSize() - kHeapObjectTag, PP); |
| 526 __ br(R2); |
| 465 } | 527 } |
| 466 | 528 |
| 467 | 529 |
| 468 void StubCode::GenerateTwoArgsUnoptimizedStaticCallStub(Assembler* assembler) { | 530 void StubCode::GenerateTwoArgsUnoptimizedStaticCallStub(Assembler* assembler) { |
| 469 __ Stop("GenerateTwoArgsUnoptimizedStaticCallStub"); | 531 __ Stop("GenerateTwoArgsUnoptimizedStaticCallStub"); |
| 470 } | 532 } |
| 471 | 533 |
| 472 | 534 |
| 473 void StubCode::GenerateLazyCompileStub(Assembler* assembler) { | 535 void StubCode::GenerateLazyCompileStub(Assembler* assembler) { |
| 474 __ Stop("GenerateLazyCompileStub"); | 536 __ Stop("GenerateLazyCompileStub"); |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 531 | 593 |
| 532 | 594 |
| 533 void StubCode::GenerateOptimizedIdenticalWithNumberCheckStub( | 595 void StubCode::GenerateOptimizedIdenticalWithNumberCheckStub( |
| 534 Assembler* assembler) { | 596 Assembler* assembler) { |
| 535 __ Stop("GenerateOptimizedIdenticalWithNumberCheckStub"); | 597 __ Stop("GenerateOptimizedIdenticalWithNumberCheckStub"); |
| 536 } | 598 } |
| 537 | 599 |
| 538 } // namespace dart | 600 } // namespace dart |
| 539 | 601 |
| 540 #endif // defined TARGET_ARCH_ARM64 | 602 #endif // defined TARGET_ARCH_ARM64 |
| OLD | NEW |