Commit cf2f6b80 authored by mbrandy's avatar mbrandy Committed by Commit bot

PPC: [turbofan] Better and more sane support for tail calls

Port ff283f7d

Original commit message:
    * Limit triggering of tail calls to explicit use of a new inline runtime
      function %_TailCall. %_TailCall works just like %_Call except for using
      tail-calling mechanics (currently only in TF).
    * Remove hack that recognized some specific usages of %_Call and converted them
      into tail calls.
    * Support tail calls for all calls where the number of callee stack parameters
      is less than or equal to the number of caller stack parameters.
    * Use the gap resolver to swizzle parameters and registers to tail calls.

R=danno@chromium.org, joransiu@ca.ibm.com, jyan@ca.ibm.com, michael_dawson@ca.ibm.com, dstence@us.ibm.com
BUG=v8:4076
LOG=n

Review URL: https://codereview.chromium.org/1442143002

Cr-Commit-Position: refs/heads/master@{#31994}
parent c0d310bd
...@@ -605,11 +605,15 @@ Condition FlagsConditionToCondition(FlagsCondition condition) { ...@@ -605,11 +605,15 @@ Condition FlagsConditionToCondition(FlagsCondition condition) {
} while (0) } while (0)
void CodeGenerator::AssembleDeconstructActivationRecord() { void CodeGenerator::AssembleDeconstructActivationRecord(int stack_param_delta) {
CallDescriptor* descriptor = linkage()->GetIncomingDescriptor(); CallDescriptor* descriptor = linkage()->GetIncomingDescriptor();
int stack_slots = frame()->GetSpillSlotCount(); int stack_slots = frame()->GetSpillSlotCount();
int sp_delta =
(stack_param_delta < 0) ? -stack_param_delta * kPointerSize : 0;
if (descriptor->IsJSFunctionCall() || stack_slots > 0) { if (descriptor->IsJSFunctionCall() || stack_slots > 0) {
__ LeaveFrame(StackFrame::MANUAL); __ LeaveFrame(StackFrame::MANUAL, sp_delta);
} else if (sp_delta) {
__ Add(sp, sp, sp_delta, r0);
} }
} }
...@@ -637,7 +641,8 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) { ...@@ -637,7 +641,8 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
break; break;
} }
case kArchTailCallCodeObject: { case kArchTailCallCodeObject: {
AssembleDeconstructActivationRecord(); int stack_param_delta = i.InputInt32(instr->InputCount() - 1);
AssembleDeconstructActivationRecord(stack_param_delta);
if (HasRegisterInput(instr, 0)) { if (HasRegisterInput(instr, 0)) {
__ addi(ip, i.InputRegister(0), __ addi(ip, i.InputRegister(0),
Operand(Code::kHeaderSize - kHeapObjectTag)); Operand(Code::kHeaderSize - kHeapObjectTag));
...@@ -679,7 +684,8 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) { ...@@ -679,7 +684,8 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
__ cmp(cp, kScratchReg); __ cmp(cp, kScratchReg);
__ Assert(eq, kWrongFunctionContext); __ Assert(eq, kWrongFunctionContext);
} }
AssembleDeconstructActivationRecord(); int stack_param_delta = i.InputInt32(instr->InputCount() - 1);
AssembleDeconstructActivationRecord(stack_param_delta);
__ LoadP(ip, FieldMemOperand(func, JSFunction::kCodeEntryOffset)); __ LoadP(ip, FieldMemOperand(func, JSFunction::kCodeEntryOffset));
__ Jump(ip); __ Jump(ip);
DCHECK_EQ(LeaveRC, i.OutputRCBit()); DCHECK_EQ(LeaveRC, i.OutputRCBit());
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment