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

Side by Side Diff: src/compiler/linkage.cc

Issue 1245523002: [turbofan]: Fix tail calls edge cases and add tests (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@1220823004
Patch Set: Cleanup tests Created 5 years, 5 months 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
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/code-stubs.h" 5 #include "src/code-stubs.h"
6 #include "src/compiler.h" 6 #include "src/compiler.h"
7 #include "src/compiler/common-operator.h" 7 #include "src/compiler/common-operator.h"
8 #include "src/compiler/linkage.h" 8 #include "src/compiler/linkage.h"
9 #include "src/compiler/node.h" 9 #include "src/compiler/node.h"
10 #include "src/compiler/pipeline.h" 10 #include "src/compiler/pipeline.h"
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
46 const CallDescriptor* other) const { 46 const CallDescriptor* other) const {
47 if (ReturnCount() != other->ReturnCount()) return false; 47 if (ReturnCount() != other->ReturnCount()) return false;
48 for (size_t i = 0; i < ReturnCount(); ++i) { 48 for (size_t i = 0; i < ReturnCount(); ++i) {
49 if (GetReturnLocation(i) != other->GetReturnLocation(i)) return false; 49 if (GetReturnLocation(i) != other->GetReturnLocation(i)) return false;
50 } 50 }
51 return true; 51 return true;
52 } 52 }
53 53
54 54
55 bool CallDescriptor::CanTailCall(const Node* node) const { 55 bool CallDescriptor::CanTailCall(const Node* node) const {
56 // Determine the number of stack parameters passed in
57 size_t stack_params = 0;
58 for (int i = 0; i < InputCount(); ++i) {
59 if (!GetInputLocation(i).is_register()) {
60 ++stack_params;
61 }
62 }
63 // Ensure the input linkage contains the stack parameters in the right order
64 size_t current_stack_param = 0;
65 for (int i = 0; i < InputCount(); ++i) {
66 if (!GetInputLocation(i).is_register()) {
67 if (GetInputLocation(i) !=
68 LinkageLocation(current_stack_param - stack_params)) {
69 return false;
70 }
71 ++current_stack_param;
72 }
73 }
56 // Tail calling is currently allowed if return locations match and all 74 // Tail calling is currently allowed if return locations match and all
57 // parameters are either in registers or on the stack but match exactly in 75 // parameters are either in registers or on the stack but match exactly in
58 // number and content. 76 // number and content.
59 CallDescriptor const* other = OpParameter<CallDescriptor const*>(node); 77 CallDescriptor const* other = OpParameter<CallDescriptor const*>(node);
60 if (!HasSameReturnLocationsAs(other)) return false; 78 if (!HasSameReturnLocationsAs(other)) return false;
61 size_t current_input = 0; 79 size_t current_input = 0;
62 size_t other_input = 0; 80 size_t other_input = 0;
63 size_t stack_parameter = 0;
64 while (true) { 81 while (true) {
65 if (other_input >= other->InputCount()) { 82 if (other_input >= other->InputCount()) {
66 while (current_input <= InputCount()) { 83 while (current_input < InputCount()) {
67 if (!GetInputLocation(current_input).is_register()) { 84 if (!GetInputLocation(current_input).is_register()) {
68 return false; 85 return false;
69 } 86 }
70 ++current_input; 87 ++current_input;
71 } 88 }
72 return true; 89 return true;
73 } 90 }
74 if (current_input >= InputCount()) { 91 if (current_input >= InputCount()) {
75 while (other_input < other->InputCount()) { 92 while (other_input < other->InputCount()) {
76 if (!other->GetInputLocation(other_input).is_register()) { 93 if (!other->GetInputLocation(other_input).is_register()) {
(...skipping 12 matching lines...) Expand all
89 continue; 106 continue;
90 } 107 }
91 if (GetInputLocation(current_input) != 108 if (GetInputLocation(current_input) !=
92 other->GetInputLocation(other_input)) { 109 other->GetInputLocation(other_input)) {
93 return false; 110 return false;
94 } 111 }
95 Node* input = node->InputAt(static_cast<int>(other_input)); 112 Node* input = node->InputAt(static_cast<int>(other_input));
96 if (input->opcode() != IrOpcode::kParameter) { 113 if (input->opcode() != IrOpcode::kParameter) {
97 return false; 114 return false;
98 } 115 }
116 // Make sure that the parameter input passed through to the tail call
117 // corresponds to the correct stack slot.
99 size_t param_index = ParameterIndexOf(input->op()); 118 size_t param_index = ParameterIndexOf(input->op());
100 if (param_index != stack_parameter) { 119 if (param_index != current_input - 1) {
101 return false; 120 return false;
102 } 121 }
103 ++stack_parameter;
104 ++current_input; 122 ++current_input;
105 ++other_input; 123 ++other_input;
106 } 124 }
107 UNREACHABLE(); 125 UNREACHABLE();
108 return false; 126 return false;
109 } 127 }
110 128
111 129
112 CallDescriptor* Linkage::ComputeIncoming(Zone* zone, CompilationInfo* info) { 130 CallDescriptor* Linkage::ComputeIncoming(Zone* zone, CompilationInfo* info) {
113 if (info->code_stub() != NULL) { 131 if (info->code_stub() != NULL) {
(...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after
263 281
264 CallDescriptor* Linkage::GetSimplifiedCDescriptor(Zone* zone, 282 CallDescriptor* Linkage::GetSimplifiedCDescriptor(Zone* zone,
265 const MachineSignature* sig) { 283 const MachineSignature* sig) {
266 UNIMPLEMENTED(); 284 UNIMPLEMENTED();
267 return NULL; 285 return NULL;
268 } 286 }
269 #endif // !V8_TURBOFAN_BACKEND 287 #endif // !V8_TURBOFAN_BACKEND
270 } // namespace compiler 288 } // namespace compiler
271 } // namespace internal 289 } // namespace internal
272 } // namespace v8 290 } // namespace v8
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698