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

Side by Side Diff: src/compiler/change-lowering.cc

Issue 1901803002: [turbofan] Remove phase ordering problem in JSToNumber lowering. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Untank Created 4 years, 8 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/compiler/change-lowering.h" 5 #include "src/compiler/change-lowering.h"
6 6
7 #include "src/address-map.h" 7 #include "src/address-map.h"
8 #include "src/code-factory.h" 8 #include "src/code-factory.h"
9 #include "src/compiler/js-graph.h" 9 #include "src/compiler/js-graph.h"
10 #include "src/compiler/linkage.h" 10 #include "src/compiler/linkage.h"
(...skipping 13 matching lines...) Expand all
24 Node* control = graph()->start(); 24 Node* control = graph()->start();
25 switch (node->opcode()) { 25 switch (node->opcode()) {
26 case IrOpcode::kChangeBitToBool: 26 case IrOpcode::kChangeBitToBool:
27 return ChangeBitToBool(node->InputAt(0), control); 27 return ChangeBitToBool(node->InputAt(0), control);
28 case IrOpcode::kChangeBoolToBit: 28 case IrOpcode::kChangeBoolToBit:
29 return ChangeBoolToBit(node->InputAt(0)); 29 return ChangeBoolToBit(node->InputAt(0));
30 case IrOpcode::kChangeFloat64ToTagged: 30 case IrOpcode::kChangeFloat64ToTagged:
31 return ChangeFloat64ToTagged(node->InputAt(0), control); 31 return ChangeFloat64ToTagged(node->InputAt(0), control);
32 case IrOpcode::kChangeInt32ToTagged: 32 case IrOpcode::kChangeInt32ToTagged:
33 return ChangeInt32ToTagged(node->InputAt(0), control); 33 return ChangeInt32ToTagged(node->InputAt(0), control);
34 case IrOpcode::kChangeTaggedSignedToWord32:
35 return ChangeTaggedSignedToWord32(node->InputAt(0));
34 case IrOpcode::kChangeTaggedToFloat64: 36 case IrOpcode::kChangeTaggedToFloat64:
35 return ChangeTaggedToFloat64(node->InputAt(0), control); 37 return ChangeTaggedToFloat64(node->InputAt(0), control);
36 case IrOpcode::kChangeTaggedToInt32: 38 case IrOpcode::kChangeTaggedToInt32:
37 return ChangeTaggedToUI32(node->InputAt(0), control, kSigned); 39 return ChangeTaggedToUI32(node->InputAt(0), control, kSigned);
38 case IrOpcode::kChangeTaggedToUint32: 40 case IrOpcode::kChangeTaggedToUint32:
39 return ChangeTaggedToUI32(node->InputAt(0), control, kUnsigned); 41 return ChangeTaggedToUI32(node->InputAt(0), control, kUnsigned);
40 case IrOpcode::kChangeUint32ToTagged: 42 case IrOpcode::kChangeUint32ToTagged:
41 return ChangeUint32ToTagged(node->InputAt(0), control); 43 return ChangeUint32ToTagged(node->InputAt(0), control);
42 case IrOpcode::kLoadField: 44 case IrOpcode::kLoadField:
43 return LoadField(node); 45 return LoadField(node);
(...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after
270 Node* if_false = graph()->NewNode(common()->IfFalse(), branch); 272 Node* if_false = graph()->NewNode(common()->IfFalse(), branch);
271 Node* vfalse = graph()->NewNode(common()->Projection(0), add); 273 Node* vfalse = graph()->NewNode(common()->Projection(0), add);
272 274
273 Node* merge = graph()->NewNode(common()->Merge(2), if_true, if_false); 275 Node* merge = graph()->NewNode(common()->Merge(2), if_true, if_false);
274 Node* phi = graph()->NewNode(common()->Phi(MachineRepresentation::kTagged, 2), 276 Node* phi = graph()->NewNode(common()->Phi(MachineRepresentation::kTagged, 2),
275 vtrue, vfalse, merge); 277 vtrue, vfalse, merge);
276 278
277 return Replace(phi); 279 return Replace(phi);
278 } 280 }
279 281
282 Reduction ChangeLowering::ChangeTaggedSignedToWord32(Node* value) {
283 return Replace(ChangeSmiToInt32(value));
284 }
280 285
281 Reduction ChangeLowering::ChangeTaggedToUI32(Node* value, Node* control, 286 Reduction ChangeLowering::ChangeTaggedToUI32(Node* value, Node* control,
282 Signedness signedness) { 287 Signedness signedness) {
283 if (NodeProperties::GetType(value)->Is(Type::TaggedSigned())) { 288 if (NodeProperties::GetType(value)->Is(Type::TaggedSigned())) {
284 return Replace(ChangeSmiToInt32(value)); 289 return Replace(ChangeSmiToInt32(value));
285 } 290 }
286 291
287 const Operator* op = (signedness == kSigned) 292 const Operator* op = (signedness == kSigned)
288 ? machine()->ChangeFloat64ToInt32() 293 ? machine()->ChangeFloat64ToInt32()
289 : machine()->ChangeFloat64ToUint32(); 294 : machine()->ChangeFloat64ToUint32();
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
327 Node* vfrom_smi = ChangeSmiToInt32(value); 332 Node* vfrom_smi = ChangeSmiToInt32(value);
328 333
329 Node* merge = graph()->NewNode(common()->Merge(2), if_not_smi, if_smi); 334 Node* merge = graph()->NewNode(common()->Merge(2), if_not_smi, if_smi);
330 Node* phi = graph()->NewNode(common()->Phi(MachineRepresentation::kWord32, 2), 335 Node* phi = graph()->NewNode(common()->Phi(MachineRepresentation::kWord32, 2),
331 vnot_smi, vfrom_smi, merge); 336 vnot_smi, vfrom_smi, merge);
332 337
333 return Replace(phi); 338 return Replace(phi);
334 } 339 }
335 340
336 341
337 namespace {
338
339 bool CanCover(Node* value, IrOpcode::Value opcode) {
340 if (value->opcode() != opcode) return false;
341 bool first = true;
342 for (Edge const edge : value->use_edges()) {
343 if (NodeProperties::IsControlEdge(edge)) continue;
344 if (NodeProperties::IsEffectEdge(edge)) continue;
345 DCHECK(NodeProperties::IsValueEdge(edge));
346 if (!first) return false;
347 first = false;
348 }
349 return true;
350 }
351
352 } // namespace
353
354
355 Reduction ChangeLowering::ChangeTaggedToFloat64(Node* value, Node* control) { 342 Reduction ChangeLowering::ChangeTaggedToFloat64(Node* value, Node* control) {
356 if (CanCover(value, IrOpcode::kJSToNumber)) {
357 // ChangeTaggedToFloat64(JSToNumber(x)) =>
358 // if IsSmi(x) then ChangeSmiToFloat64(x)
359 // else let y = JSToNumber(x) in
360 // if IsSmi(y) then ChangeSmiToFloat64(y)
361 // else LoadHeapNumberValue(y)
362 Node* const object = NodeProperties::GetValueInput(value, 0);
363 Node* const context = NodeProperties::GetContextInput(value);
364 Node* const frame_state = NodeProperties::GetFrameStateInput(value, 0);
365 Node* const effect = NodeProperties::GetEffectInput(value);
366 Node* const control = NodeProperties::GetControlInput(value);
367
368 const Operator* merge_op = common()->Merge(2);
369 const Operator* ephi_op = common()->EffectPhi(2);
370 const Operator* phi_op = common()->Phi(MachineRepresentation::kFloat64, 2);
371
372 Node* check1 = TestNotSmi(object);
373 Node* branch1 =
374 graph()->NewNode(common()->Branch(BranchHint::kFalse), check1, control);
375
376 Node* if_true1 = graph()->NewNode(common()->IfTrue(), branch1);
377 Node* vtrue1 = graph()->NewNode(value->op(), object, context, frame_state,
378 effect, if_true1);
379 Node* etrue1 = vtrue1;
380
381 Node* check2 = TestNotSmi(vtrue1);
382 Node* branch2 = graph()->NewNode(common()->Branch(), check2, if_true1);
383
384 Node* if_true2 = graph()->NewNode(common()->IfTrue(), branch2);
385 Node* vtrue2 = LoadHeapNumberValue(vtrue1, if_true2);
386
387 Node* if_false2 = graph()->NewNode(common()->IfFalse(), branch2);
388 Node* vfalse2 = ChangeSmiToFloat64(vtrue1);
389
390 if_true1 = graph()->NewNode(merge_op, if_true2, if_false2);
391 vtrue1 = graph()->NewNode(phi_op, vtrue2, vfalse2, if_true1);
392
393 Node* if_false1 = graph()->NewNode(common()->IfFalse(), branch1);
394 Node* vfalse1 = ChangeSmiToFloat64(object);
395 Node* efalse1 = effect;
396
397 Node* merge1 = graph()->NewNode(merge_op, if_true1, if_false1);
398 Node* ephi1 = graph()->NewNode(ephi_op, etrue1, efalse1, merge1);
399 Node* phi1 = graph()->NewNode(phi_op, vtrue1, vfalse1, merge1);
400
401 // Wire the new diamond into the graph, {JSToNumber} can still throw.
402 NodeProperties::ReplaceUses(value, phi1, ephi1, etrue1, etrue1);
403
404 // TODO(mstarzinger): This iteration cuts out the IfSuccess projection from
405 // the node and places it inside the diamond. Come up with a helper method!
406 for (Node* use : etrue1->uses()) {
407 if (use->opcode() == IrOpcode::kIfSuccess) {
408 use->ReplaceUses(merge1);
409 NodeProperties::ReplaceControlInput(branch2, use);
410 }
411 }
412
413 return Replace(phi1);
414 }
415
416 Node* check = TestNotSmi(value); 343 Node* check = TestNotSmi(value);
417 Node* branch = 344 Node* branch =
418 graph()->NewNode(common()->Branch(BranchHint::kFalse), check, control); 345 graph()->NewNode(common()->Branch(BranchHint::kFalse), check, control);
419 346
420 Node* if_not_smi = graph()->NewNode(common()->IfTrue(), branch); 347 Node* if_not_smi = graph()->NewNode(common()->IfTrue(), branch);
421 348
422 Node* vnot_smi; 349 Node* vnot_smi;
423 if (NodeProperties::GetType(value)->Maybe(Type::Undefined())) { 350 if (NodeProperties::GetType(value)->Maybe(Type::Undefined())) {
424 Node* check_undefined = graph()->NewNode(machine()->WordEqual(), value, 351 Node* check_undefined = graph()->NewNode(machine()->WordEqual(), value,
425 jsgraph()->UndefinedConstant()); 352 jsgraph()->UndefinedConstant());
(...skipping 355 matching lines...) Expand 10 before | Expand all | Expand 10 after
781 } 708 }
782 709
783 710
784 MachineOperatorBuilder* ChangeLowering::machine() const { 711 MachineOperatorBuilder* ChangeLowering::machine() const {
785 return jsgraph()->machine(); 712 return jsgraph()->machine();
786 } 713 }
787 714
788 } // namespace compiler 715 } // namespace compiler
789 } // namespace internal 716 } // namespace internal
790 } // namespace v8 717 } // namespace v8
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698