| OLD | NEW |
| 1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 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-stub-assembler.h" | 5 #include "src/compiler/code-stub-assembler.h" |
| 6 | 6 |
| 7 #include <ostream> | 7 #include <ostream> |
| 8 | 8 |
| 9 #include "src/code-factory.h" | 9 #include "src/code-factory.h" |
| 10 #include "src/compiler/graph.h" | 10 #include "src/compiler/graph.h" |
| (...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 156 } | 156 } |
| 157 | 157 |
| 158 Node* CodeStubAssembler::SmiToFloat64(Node* value) { | 158 Node* CodeStubAssembler::SmiToFloat64(Node* value) { |
| 159 return ChangeInt32ToFloat64(SmiUntag(value)); | 159 return ChangeInt32ToFloat64(SmiUntag(value)); |
| 160 } | 160 } |
| 161 | 161 |
| 162 Node* CodeStubAssembler::SmiAdd(Node* a, Node* b) { return IntPtrAdd(a, b); } | 162 Node* CodeStubAssembler::SmiAdd(Node* a, Node* b) { return IntPtrAdd(a, b); } |
| 163 | 163 |
| 164 Node* CodeStubAssembler::SmiEqual(Node* a, Node* b) { return WordEqual(a, b); } | 164 Node* CodeStubAssembler::SmiEqual(Node* a, Node* b) { return WordEqual(a, b); } |
| 165 | 165 |
| 166 Node* CodeStubAssembler::SmiLessThan(Node* a, Node* b) { |
| 167 return IntPtrLessThan(a, b); |
| 168 } |
| 169 |
| 170 Node* CodeStubAssembler::SmiLessThanOrEqual(Node* a, Node* b) { |
| 171 return IntPtrLessThanOrEqual(a, b); |
| 172 } |
| 173 |
| 166 #define DEFINE_CODE_STUB_ASSEMBER_BINARY_OP(name) \ | 174 #define DEFINE_CODE_STUB_ASSEMBER_BINARY_OP(name) \ |
| 167 Node* CodeStubAssembler::name(Node* a, Node* b) { \ | 175 Node* CodeStubAssembler::name(Node* a, Node* b) { \ |
| 168 return raw_assembler_->name(a, b); \ | 176 return raw_assembler_->name(a, b); \ |
| 169 } | 177 } |
| 170 CODE_STUB_ASSEMBLER_BINARY_OP_LIST(DEFINE_CODE_STUB_ASSEMBER_BINARY_OP) | 178 CODE_STUB_ASSEMBLER_BINARY_OP_LIST(DEFINE_CODE_STUB_ASSEMBER_BINARY_OP) |
| 171 #undef DEFINE_CODE_STUB_ASSEMBER_BINARY_OP | 179 #undef DEFINE_CODE_STUB_ASSEMBER_BINARY_OP |
| 172 | 180 |
| 173 Node* CodeStubAssembler::WordShl(Node* value, int shift) { | 181 Node* CodeStubAssembler::WordShl(Node* value, int shift) { |
| 174 return raw_assembler_->WordShl(value, IntPtrConstant(shift)); | 182 return raw_assembler_->WordShl(value, IntPtrConstant(shift)); |
| 175 } | 183 } |
| (...skipping 233 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 409 return LoadMapInstanceType(LoadObjectField(object, HeapObject::kMapOffset)); | 417 return LoadMapInstanceType(LoadObjectField(object, HeapObject::kMapOffset)); |
| 410 } | 418 } |
| 411 | 419 |
| 412 Node* CodeStubAssembler::BitFieldDecode(Node* word32, uint32_t shift, | 420 Node* CodeStubAssembler::BitFieldDecode(Node* word32, uint32_t shift, |
| 413 uint32_t mask) { | 421 uint32_t mask) { |
| 414 return raw_assembler_->Word32Shr( | 422 return raw_assembler_->Word32Shr( |
| 415 raw_assembler_->Word32And(word32, raw_assembler_->Int32Constant(mask)), | 423 raw_assembler_->Word32And(word32, raw_assembler_->Int32Constant(mask)), |
| 416 raw_assembler_->Int32Constant(shift)); | 424 raw_assembler_->Int32Constant(shift)); |
| 417 } | 425 } |
| 418 | 426 |
| 427 void CodeStubAssembler::BranchIfSmiLessThan(Node* a, Node* b, Label* if_true, |
| 428 Label* if_false) { |
| 429 Label if_lessthan(this), if_notlessthan(this); |
| 430 Branch(SmiLessThan(a, b), &if_lessthan, &if_notlessthan); |
| 431 Bind(&if_lessthan); |
| 432 Goto(if_true); |
| 433 Bind(&if_notlessthan); |
| 434 Goto(if_false); |
| 435 } |
| 436 |
| 437 void CodeStubAssembler::BranchIfSmiLessThanOrEqual(Node* a, Node* b, |
| 438 Label* if_true, |
| 439 Label* if_false) { |
| 440 Label if_lessthanorequal(this), if_notlessthanorequal(this); |
| 441 Branch(SmiLessThanOrEqual(a, b), &if_lessthanorequal, &if_notlessthanorequal); |
| 442 Bind(&if_lessthanorequal); |
| 443 Goto(if_true); |
| 444 Bind(&if_notlessthanorequal); |
| 445 Goto(if_false); |
| 446 } |
| 447 |
| 419 void CodeStubAssembler::BranchIfFloat64Equal(Node* a, Node* b, Label* if_true, | 448 void CodeStubAssembler::BranchIfFloat64Equal(Node* a, Node* b, Label* if_true, |
| 420 Label* if_false) { | 449 Label* if_false) { |
| 421 Label if_equal(this), if_notequal(this); | 450 Label if_equal(this), if_notequal(this); |
| 422 Branch(Float64Equal(a, b), &if_equal, &if_notequal); | 451 Branch(Float64Equal(a, b), &if_equal, &if_notequal); |
| 423 Bind(&if_equal); | 452 Bind(&if_equal); |
| 424 Goto(if_true); | 453 Goto(if_true); |
| 425 Bind(&if_notequal); | 454 Bind(&if_notequal); |
| 426 Goto(if_false); | 455 Goto(if_false); |
| 427 } | 456 } |
| 428 | 457 |
| 458 void CodeStubAssembler::BranchIfFloat64LessThan(Node* a, Node* b, |
| 459 Label* if_true, |
| 460 Label* if_false) { |
| 461 Label if_lessthan(this), if_notlessthan(this); |
| 462 Branch(Float64LessThan(a, b), &if_lessthan, &if_notlessthan); |
| 463 Bind(&if_lessthan); |
| 464 Goto(if_true); |
| 465 Bind(&if_notlessthan); |
| 466 Goto(if_false); |
| 467 } |
| 468 |
| 469 void CodeStubAssembler::BranchIfFloat64LessThanOrEqual(Node* a, Node* b, |
| 470 Label* if_true, |
| 471 Label* if_false) { |
| 472 Label if_lessthanorequal(this), if_notlessthanorequal(this); |
| 473 Branch(Float64LessThanOrEqual(a, b), &if_lessthanorequal, |
| 474 &if_notlessthanorequal); |
| 475 Bind(&if_lessthanorequal); |
| 476 Goto(if_true); |
| 477 Bind(&if_notlessthanorequal); |
| 478 Goto(if_false); |
| 479 } |
| 480 |
| 481 void CodeStubAssembler::BranchIfFloat64GreaterThan(Node* a, Node* b, |
| 482 Label* if_true, |
| 483 Label* if_false) { |
| 484 Label if_greaterthan(this), if_notgreaterthan(this); |
| 485 Branch(Float64GreaterThan(a, b), &if_greaterthan, &if_notgreaterthan); |
| 486 Bind(&if_greaterthan); |
| 487 Goto(if_true); |
| 488 Bind(&if_notgreaterthan); |
| 489 Goto(if_false); |
| 490 } |
| 491 |
| 492 void CodeStubAssembler::BranchIfFloat64GreaterThanOrEqual(Node* a, Node* b, |
| 493 Label* if_true, |
| 494 Label* if_false) { |
| 495 Label if_greaterthanorequal(this), if_notgreaterthanorequal(this); |
| 496 Branch(Float64GreaterThanOrEqual(a, b), &if_greaterthanorequal, |
| 497 &if_notgreaterthanorequal); |
| 498 Bind(&if_greaterthanorequal); |
| 499 Goto(if_true); |
| 500 Bind(&if_notgreaterthanorequal); |
| 501 Goto(if_false); |
| 502 } |
| 503 |
| 429 Node* CodeStubAssembler::CallN(CallDescriptor* descriptor, Node* code_target, | 504 Node* CodeStubAssembler::CallN(CallDescriptor* descriptor, Node* code_target, |
| 430 Node** args) { | 505 Node** args) { |
| 431 CallPrologue(); | 506 CallPrologue(); |
| 432 Node* return_value = raw_assembler_->CallN(descriptor, code_target, args); | 507 Node* return_value = raw_assembler_->CallN(descriptor, code_target, args); |
| 433 CallEpilogue(); | 508 CallEpilogue(); |
| 434 return return_value; | 509 return return_value; |
| 435 } | 510 } |
| 436 | 511 |
| 437 | 512 |
| 438 Node* CodeStubAssembler::TailCallN(CallDescriptor* descriptor, | 513 Node* CodeStubAssembler::TailCallN(CallDescriptor* descriptor, |
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 508 context); | 583 context); |
| 509 } | 584 } |
| 510 | 585 |
| 511 Node* CodeStubAssembler::TailCallRuntime(Runtime::FunctionId function_id, | 586 Node* CodeStubAssembler::TailCallRuntime(Runtime::FunctionId function_id, |
| 512 Node* context, Node* arg1, Node* arg2, | 587 Node* context, Node* arg1, Node* arg2, |
| 513 Node* arg3, Node* arg4) { | 588 Node* arg3, Node* arg4) { |
| 514 return raw_assembler_->TailCallRuntime4(function_id, arg1, arg2, arg3, arg4, | 589 return raw_assembler_->TailCallRuntime4(function_id, arg1, arg2, arg3, arg4, |
| 515 context); | 590 context); |
| 516 } | 591 } |
| 517 | 592 |
| 593 Node* CodeStubAssembler::CallStub(Callable const& callable, Node* context, |
| 594 Node* arg1, size_t result_size) { |
| 595 Node* target = HeapConstant(callable.code()); |
| 596 return CallStub(callable.descriptor(), target, context, arg1, result_size); |
| 597 } |
| 598 |
| 518 Node* CodeStubAssembler::CallStub(const CallInterfaceDescriptor& descriptor, | 599 Node* CodeStubAssembler::CallStub(const CallInterfaceDescriptor& descriptor, |
| 519 Node* target, Node* context, Node* arg1, | 600 Node* target, Node* context, Node* arg1, |
| 520 size_t result_size) { | 601 size_t result_size) { |
| 521 CallDescriptor* call_descriptor = Linkage::GetStubCallDescriptor( | 602 CallDescriptor* call_descriptor = Linkage::GetStubCallDescriptor( |
| 522 isolate(), zone(), descriptor, descriptor.GetStackParameterCount(), | 603 isolate(), zone(), descriptor, descriptor.GetStackParameterCount(), |
| 523 CallDescriptor::kNoFlags, Operator::kNoProperties, | 604 CallDescriptor::kNoFlags, Operator::kNoProperties, |
| 524 MachineType::AnyTagged(), result_size); | 605 MachineType::AnyTagged(), result_size); |
| 525 | 606 |
| 526 Node** args = zone()->NewArray<Node*>(2); | 607 Node** args = zone()->NewArray<Node*>(2); |
| 527 args[0] = arg1; | 608 args[0] = arg1; |
| (...skipping 174 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 702 } | 783 } |
| 703 | 784 |
| 704 MachineRepresentation CodeStubAssembler::Variable::rep() const { | 785 MachineRepresentation CodeStubAssembler::Variable::rep() const { |
| 705 return impl_->rep_; | 786 return impl_->rep_; |
| 706 } | 787 } |
| 707 | 788 |
| 708 bool CodeStubAssembler::Variable::IsBound() const { | 789 bool CodeStubAssembler::Variable::IsBound() const { |
| 709 return impl_->value_ != nullptr; | 790 return impl_->value_ != nullptr; |
| 710 } | 791 } |
| 711 | 792 |
| 712 CodeStubAssembler::Label::Label(CodeStubAssembler* assembler) | |
| 713 : bound_(false), merge_count_(0), assembler_(assembler), label_(nullptr) { | |
| 714 void* buffer = assembler->zone()->New(sizeof(RawMachineLabel)); | |
| 715 label_ = new (buffer) RawMachineLabel(); | |
| 716 } | |
| 717 | |
| 718 CodeStubAssembler::Label::Label(CodeStubAssembler* assembler, | 793 CodeStubAssembler::Label::Label(CodeStubAssembler* assembler, |
| 719 int merged_value_count, | 794 int merged_value_count, |
| 720 CodeStubAssembler::Variable** merged_variables) | 795 CodeStubAssembler::Variable** merged_variables, |
| 796 CodeStubAssembler::Label::Type type) |
| 721 : bound_(false), merge_count_(0), assembler_(assembler), label_(nullptr) { | 797 : bound_(false), merge_count_(0), assembler_(assembler), label_(nullptr) { |
| 722 void* buffer = assembler->zone()->New(sizeof(RawMachineLabel)); | 798 void* buffer = assembler->zone()->New(sizeof(RawMachineLabel)); |
| 723 label_ = new (buffer) RawMachineLabel(); | 799 label_ = new (buffer) |
| 800 RawMachineLabel(type == kDeferred ? RawMachineLabel::kDeferred |
| 801 : RawMachineLabel::kNonDeferred); |
| 724 for (int i = 0; i < merged_value_count; ++i) { | 802 for (int i = 0; i < merged_value_count; ++i) { |
| 725 variable_phis_[merged_variables[i]->impl_] = nullptr; | 803 variable_phis_[merged_variables[i]->impl_] = nullptr; |
| 726 } | 804 } |
| 727 } | 805 } |
| 728 | 806 |
| 729 CodeStubAssembler::Label::Label(CodeStubAssembler* assembler, | |
| 730 CodeStubAssembler::Variable* merged_variable) | |
| 731 : CodeStubAssembler::Label(assembler, 1, &merged_variable) {} | |
| 732 | |
| 733 void CodeStubAssembler::Label::MergeVariables() { | 807 void CodeStubAssembler::Label::MergeVariables() { |
| 734 ++merge_count_; | 808 ++merge_count_; |
| 735 for (auto var : assembler_->variables_) { | 809 for (auto var : assembler_->variables_) { |
| 736 size_t count = 0; | 810 size_t count = 0; |
| 737 Node* node = var->value_; | 811 Node* node = var->value_; |
| 738 if (node != nullptr) { | 812 if (node != nullptr) { |
| 739 auto i = variable_merges_.find(var); | 813 auto i = variable_merges_.find(var); |
| 740 if (i != variable_merges_.end()) { | 814 if (i != variable_merges_.end()) { |
| 741 i->second.push_back(node); | 815 i->second.push_back(node); |
| 742 count = i->second.size(); | 816 count = i->second.size(); |
| (...skipping 10 matching lines...) Expand all Loading... |
| 753 | 827 |
| 754 // If the label is already bound, we already know the set of variables to | 828 // If the label is already bound, we already know the set of variables to |
| 755 // merge and phi nodes have already been created. | 829 // merge and phi nodes have already been created. |
| 756 if (bound_) { | 830 if (bound_) { |
| 757 auto phi = variable_phis_.find(var); | 831 auto phi = variable_phis_.find(var); |
| 758 if (phi != variable_phis_.end()) { | 832 if (phi != variable_phis_.end()) { |
| 759 DCHECK_NOT_NULL(phi->second); | 833 DCHECK_NOT_NULL(phi->second); |
| 760 assembler_->raw_assembler_->AppendPhiInput(phi->second, node); | 834 assembler_->raw_assembler_->AppendPhiInput(phi->second, node); |
| 761 } else { | 835 } else { |
| 762 auto i = variable_merges_.find(var); | 836 auto i = variable_merges_.find(var); |
| 763 USE(i); | 837 if (i != variable_merges_.end()) { |
| 764 // If the following assert fires, then you've declared a variable that | 838 // If the following assert fires, then you've declared a variable that |
| 765 // has the same bound value along all paths up until the point you bound | 839 // has the same bound value along all paths up until the point you |
| 766 // this label, but then later merged a path with a new value for the | 840 // bound this label, but then later merged a path with a new value for |
| 767 // variable after the label bind (it's not possible to add phis to the | 841 // the variable after the label bind (it's not possible to add phis to |
| 768 // bound label after the fact, just make sure to list the variable in | 842 // the bound label after the fact, just make sure to list the variable |
| 769 // the label's constructor's list of merged variables). | 843 // in the label's constructor's list of merged variables). |
| 770 DCHECK(find_if(i->second.begin(), i->second.end(), | 844 DCHECK(find_if(i->second.begin(), i->second.end(), |
| 771 [node](Node* e) -> bool { return node != e; }) == | 845 [node](Node* e) -> bool { return node != e; }) == |
| 772 i->second.end()); | 846 i->second.end()); |
| 847 } |
| 773 } | 848 } |
| 774 } | 849 } |
| 775 } | 850 } |
| 776 } | 851 } |
| 777 | 852 |
| 778 void CodeStubAssembler::Label::Bind() { | 853 void CodeStubAssembler::Label::Bind() { |
| 779 DCHECK(!bound_); | 854 DCHECK(!bound_); |
| 780 assembler_->raw_assembler_->Bind(label_); | 855 assembler_->raw_assembler_->Bind(label_); |
| 781 | 856 |
| 782 // Make sure that all variables that have changed along any path up to this | 857 // Make sure that all variables that have changed along any path up to this |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 827 } | 902 } |
| 828 } | 903 } |
| 829 } | 904 } |
| 830 | 905 |
| 831 bound_ = true; | 906 bound_ = true; |
| 832 } | 907 } |
| 833 | 908 |
| 834 } // namespace compiler | 909 } // namespace compiler |
| 835 } // namespace internal | 910 } // namespace internal |
| 836 } // namespace v8 | 911 } // namespace v8 |
| OLD | NEW |