Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1)

Side by Side Diff: src/compiler/ppc/code-generator-ppc.cc

Issue 1442143002: PPC: [turbofan] Better and more sane support for tail calls (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 the V8 project authors. All rights reserved. 1 // Copyright 2014 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 #include "src/compiler/code-generator.h" 5 #include "src/compiler/code-generator.h"
6 6
7 #include "src/compiler/code-generator-impl.h" 7 #include "src/compiler/code-generator-impl.h"
8 #include "src/compiler/gap-resolver.h" 8 #include "src/compiler/gap-resolver.h"
9 #include "src/compiler/node-matchers.h" 9 #include "src/compiler/node-matchers.h"
10 #include "src/compiler/osr.h" 10 #include "src/compiler/osr.h"
(...skipping 587 matching lines...) Expand 10 before | Expand all | Expand 10 after
598 if (mode == kMode_MRI) { \ 598 if (mode == kMode_MRI) { \
599 __ asm_instr(value, operand); \ 599 __ asm_instr(value, operand); \
600 } else { \ 600 } else { \
601 __ asm_instrx(value, operand); \ 601 __ asm_instrx(value, operand); \
602 } \ 602 } \
603 __ bind(&done); \ 603 __ bind(&done); \
604 DCHECK_EQ(LeaveRC, i.OutputRCBit()); \ 604 DCHECK_EQ(LeaveRC, i.OutputRCBit()); \
605 } while (0) 605 } while (0)
606 606
607 607
608 void CodeGenerator::AssembleDeconstructActivationRecord() { 608 void CodeGenerator::AssembleDeconstructActivationRecord(int stack_param_delta) {
609 CallDescriptor* descriptor = linkage()->GetIncomingDescriptor(); 609 CallDescriptor* descriptor = linkage()->GetIncomingDescriptor();
610 int stack_slots = frame()->GetSpillSlotCount(); 610 int stack_slots = frame()->GetSpillSlotCount();
611 int sp_delta =
612 (stack_param_delta < 0) ? -stack_param_delta * kPointerSize : 0;
611 if (descriptor->IsJSFunctionCall() || stack_slots > 0) { 613 if (descriptor->IsJSFunctionCall() || stack_slots > 0) {
612 __ LeaveFrame(StackFrame::MANUAL); 614 __ LeaveFrame(StackFrame::MANUAL, sp_delta);
615 } else if (sp_delta) {
616 __ Add(sp, sp, sp_delta, r0);
613 } 617 }
614 } 618 }
615 619
616 620
617 // Assembles an instruction after register allocation, producing machine code. 621 // Assembles an instruction after register allocation, producing machine code.
618 void CodeGenerator::AssembleArchInstruction(Instruction* instr) { 622 void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
619 PPCOperandConverter i(this, instr); 623 PPCOperandConverter i(this, instr);
620 ArchOpcode opcode = ArchOpcodeField::decode(instr->opcode()); 624 ArchOpcode opcode = ArchOpcodeField::decode(instr->opcode());
621 625
622 switch (opcode) { 626 switch (opcode) {
623 case kArchCallCodeObject: { 627 case kArchCallCodeObject: {
624 v8::internal::Assembler::BlockTrampolinePoolScope block_trampoline_pool( 628 v8::internal::Assembler::BlockTrampolinePoolScope block_trampoline_pool(
625 masm()); 629 masm());
626 EnsureSpaceForLazyDeopt(); 630 EnsureSpaceForLazyDeopt();
627 if (HasRegisterInput(instr, 0)) { 631 if (HasRegisterInput(instr, 0)) {
628 __ addi(ip, i.InputRegister(0), 632 __ addi(ip, i.InputRegister(0),
629 Operand(Code::kHeaderSize - kHeapObjectTag)); 633 Operand(Code::kHeaderSize - kHeapObjectTag));
630 __ Call(ip); 634 __ Call(ip);
631 } else { 635 } else {
632 __ Call(Handle<Code>::cast(i.InputHeapObject(0)), 636 __ Call(Handle<Code>::cast(i.InputHeapObject(0)),
633 RelocInfo::CODE_TARGET); 637 RelocInfo::CODE_TARGET);
634 } 638 }
635 RecordCallPosition(instr); 639 RecordCallPosition(instr);
636 DCHECK_EQ(LeaveRC, i.OutputRCBit()); 640 DCHECK_EQ(LeaveRC, i.OutputRCBit());
637 break; 641 break;
638 } 642 }
639 case kArchTailCallCodeObject: { 643 case kArchTailCallCodeObject: {
640 AssembleDeconstructActivationRecord(); 644 int stack_param_delta = i.InputInt32(instr->InputCount() - 1);
645 AssembleDeconstructActivationRecord(stack_param_delta);
641 if (HasRegisterInput(instr, 0)) { 646 if (HasRegisterInput(instr, 0)) {
642 __ addi(ip, i.InputRegister(0), 647 __ addi(ip, i.InputRegister(0),
643 Operand(Code::kHeaderSize - kHeapObjectTag)); 648 Operand(Code::kHeaderSize - kHeapObjectTag));
644 __ Jump(ip); 649 __ Jump(ip);
645 } else { 650 } else {
646 // We cannot use the constant pool to load the target since 651 // We cannot use the constant pool to load the target since
647 // we've already restored the caller's frame. 652 // we've already restored the caller's frame.
648 ConstantPoolUnavailableScope constant_pool_unavailable(masm()); 653 ConstantPoolUnavailableScope constant_pool_unavailable(masm());
649 __ Jump(Handle<Code>::cast(i.InputHeapObject(0)), 654 __ Jump(Handle<Code>::cast(i.InputHeapObject(0)),
650 RelocInfo::CODE_TARGET); 655 RelocInfo::CODE_TARGET);
(...skipping 21 matching lines...) Expand all
672 } 677 }
673 case kArchTailCallJSFunction: { 678 case kArchTailCallJSFunction: {
674 Register func = i.InputRegister(0); 679 Register func = i.InputRegister(0);
675 if (FLAG_debug_code) { 680 if (FLAG_debug_code) {
676 // Check the function's context matches the context argument. 681 // Check the function's context matches the context argument.
677 __ LoadP(kScratchReg, 682 __ LoadP(kScratchReg,
678 FieldMemOperand(func, JSFunction::kContextOffset)); 683 FieldMemOperand(func, JSFunction::kContextOffset));
679 __ cmp(cp, kScratchReg); 684 __ cmp(cp, kScratchReg);
680 __ Assert(eq, kWrongFunctionContext); 685 __ Assert(eq, kWrongFunctionContext);
681 } 686 }
682 AssembleDeconstructActivationRecord(); 687 int stack_param_delta = i.InputInt32(instr->InputCount() - 1);
688 AssembleDeconstructActivationRecord(stack_param_delta);
683 __ LoadP(ip, FieldMemOperand(func, JSFunction::kCodeEntryOffset)); 689 __ LoadP(ip, FieldMemOperand(func, JSFunction::kCodeEntryOffset));
684 __ Jump(ip); 690 __ Jump(ip);
685 DCHECK_EQ(LeaveRC, i.OutputRCBit()); 691 DCHECK_EQ(LeaveRC, i.OutputRCBit());
686 break; 692 break;
687 } 693 }
688 case kArchLazyBailout: { 694 case kArchLazyBailout: {
689 v8::internal::Assembler::BlockTrampolinePoolScope block_trampoline_pool( 695 v8::internal::Assembler::BlockTrampolinePoolScope block_trampoline_pool(
690 masm()); 696 masm());
691 EnsureSpaceForLazyDeopt(); 697 EnsureSpaceForLazyDeopt();
692 RecordCallPosition(instr); 698 RecordCallPosition(instr);
(...skipping 1030 matching lines...) Expand 10 before | Expand all | Expand 10 after
1723 padding_size -= v8::internal::Assembler::kInstrSize; 1729 padding_size -= v8::internal::Assembler::kInstrSize;
1724 } 1730 }
1725 } 1731 }
1726 } 1732 }
1727 1733
1728 #undef __ 1734 #undef __
1729 1735
1730 } // namespace compiler 1736 } // namespace compiler
1731 } // namespace internal 1737 } // namespace internal
1732 } // namespace v8 1738 } // namespace v8
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698