OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 800 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
811 } | 811 } |
812 builder_->set_current_block(first_true_block_); | 812 builder_->set_current_block(first_true_block_); |
813 } | 813 } |
814 | 814 |
815 | 815 |
816 void HGraphBuilder::IfBuilder::Else() { | 816 void HGraphBuilder::IfBuilder::Else() { |
817 ASSERT(did_then_); | 817 ASSERT(did_then_); |
818 ASSERT(!captured_); | 818 ASSERT(!captured_); |
819 ASSERT(!finished_); | 819 ASSERT(!finished_); |
820 last_true_block_ = builder_->current_block(); | 820 last_true_block_ = builder_->current_block(); |
821 ASSERT(first_true_block_ == NULL || !last_true_block_->IsFinished()); | |
822 builder_->set_current_block(first_false_block_); | 821 builder_->set_current_block(first_false_block_); |
823 did_else_ = true; | 822 did_else_ = true; |
824 } | 823 } |
825 | 824 |
826 | 825 |
827 void HGraphBuilder::IfBuilder::Deopt() { | 826 void HGraphBuilder::IfBuilder::Deopt() { |
828 ASSERT(did_then_); | 827 ASSERT(did_then_); |
829 if (did_else_) { | 828 if (did_else_) { |
830 deopt_else_ = true; | 829 deopt_else_ = true; |
831 } else { | 830 } else { |
(...skipping 15 matching lines...) Expand all Loading... |
847 } | 846 } |
848 } | 847 } |
849 | 848 |
850 | 849 |
851 void HGraphBuilder::IfBuilder::End() { | 850 void HGraphBuilder::IfBuilder::End() { |
852 if (!captured_) { | 851 if (!captured_) { |
853 ASSERT(did_then_); | 852 ASSERT(did_then_); |
854 if (!did_else_) { | 853 if (!did_else_) { |
855 last_true_block_ = builder_->current_block(); | 854 last_true_block_ = builder_->current_block(); |
856 } | 855 } |
857 if (first_true_block_ == NULL) { | 856 if (last_true_block_ == NULL || last_true_block_->IsFinished()) { |
| 857 ASSERT(did_else_); |
858 // Return on true. Nothing to do, just continue the false block. | 858 // Return on true. Nothing to do, just continue the false block. |
859 } else if (first_false_block_ == NULL) { | 859 } else if (first_false_block_ == NULL || |
| 860 (did_else_ && builder_->current_block()->IsFinished())) { |
860 // Deopt on false. Nothing to do except switching to the true block. | 861 // Deopt on false. Nothing to do except switching to the true block. |
861 builder_->set_current_block(last_true_block_); | 862 builder_->set_current_block(last_true_block_); |
862 } else { | 863 } else { |
863 merge_block_ = builder_->graph()->CreateBasicBlock(); | 864 merge_block_ = builder_->graph()->CreateBasicBlock(); |
864 ASSERT(!finished_); | 865 ASSERT(!finished_); |
865 if (!did_else_) Else(); | 866 if (!did_else_) Else(); |
866 ASSERT(!last_true_block_->IsFinished()); | 867 ASSERT(!last_true_block_->IsFinished()); |
867 HBasicBlock* last_false_block = builder_->current_block(); | 868 HBasicBlock* last_false_block = builder_->current_block(); |
868 ASSERT(!last_false_block->IsFinished()); | 869 ASSERT(!last_false_block->IsFinished()); |
869 if (deopt_then_) { | 870 if (deopt_then_) { |
(...skipping 19 matching lines...) Expand all Loading... |
889 HGraphBuilder::LoopBuilder::LoopBuilder(HGraphBuilder* builder, | 890 HGraphBuilder::LoopBuilder::LoopBuilder(HGraphBuilder* builder, |
890 HValue* context, | 891 HValue* context, |
891 LoopBuilder::Direction direction) | 892 LoopBuilder::Direction direction) |
892 : builder_(builder), | 893 : builder_(builder), |
893 context_(context), | 894 context_(context), |
894 direction_(direction), | 895 direction_(direction), |
895 finished_(false) { | 896 finished_(false) { |
896 header_block_ = builder->CreateLoopHeaderBlock(); | 897 header_block_ = builder->CreateLoopHeaderBlock(); |
897 body_block_ = NULL; | 898 body_block_ = NULL; |
898 exit_block_ = NULL; | 899 exit_block_ = NULL; |
| 900 exit_trampoline_block_ = NULL; |
| 901 increment_amount_ = builder_->graph()->GetConstant1(); |
899 } | 902 } |
900 | 903 |
901 | 904 |
| 905 HGraphBuilder::LoopBuilder::LoopBuilder(HGraphBuilder* builder, |
| 906 HValue* context, |
| 907 LoopBuilder::Direction direction, |
| 908 HValue* increment_amount) |
| 909 : builder_(builder), |
| 910 context_(context), |
| 911 direction_(direction), |
| 912 finished_(false) { |
| 913 header_block_ = builder->CreateLoopHeaderBlock(); |
| 914 body_block_ = NULL; |
| 915 exit_block_ = NULL; |
| 916 exit_trampoline_block_ = NULL; |
| 917 increment_amount_ = increment_amount; |
| 918 } |
| 919 |
| 920 |
902 HValue* HGraphBuilder::LoopBuilder::BeginBody( | 921 HValue* HGraphBuilder::LoopBuilder::BeginBody( |
903 HValue* initial, | 922 HValue* initial, |
904 HValue* terminating, | 923 HValue* terminating, |
905 Token::Value token) { | 924 Token::Value token) { |
906 HEnvironment* env = builder_->environment(); | 925 HEnvironment* env = builder_->environment(); |
907 phi_ = new(zone()) HPhi(env->values()->length(), zone()); | 926 phi_ = new(zone()) HPhi(env->values()->length(), zone()); |
908 header_block_->AddPhi(phi_); | 927 header_block_->AddPhi(phi_); |
909 phi_->AddInput(initial); | 928 phi_->AddInput(initial); |
910 env->Push(initial); | 929 env->Push(initial); |
911 builder_->current_block()->GotoNoSimulate(header_block_); | 930 builder_->current_block()->GotoNoSimulate(header_block_); |
912 | 931 |
913 HEnvironment* body_env = env->Copy(); | 932 HEnvironment* body_env = env->Copy(); |
914 HEnvironment* exit_env = env->Copy(); | 933 HEnvironment* exit_env = env->Copy(); |
| 934 // Remove the phi from the expression stack |
| 935 body_env->Pop(); |
| 936 exit_env->Pop(); |
915 body_block_ = builder_->CreateBasicBlock(body_env); | 937 body_block_ = builder_->CreateBasicBlock(body_env); |
916 exit_block_ = builder_->CreateBasicBlock(exit_env); | 938 exit_block_ = builder_->CreateBasicBlock(exit_env); |
917 // Remove the phi from the expression stack | |
918 body_env->Pop(); | |
919 | 939 |
920 builder_->set_current_block(header_block_); | 940 builder_->set_current_block(header_block_); |
| 941 env->Pop(); |
921 HCompareNumericAndBranch* compare = | 942 HCompareNumericAndBranch* compare = |
922 new(zone()) HCompareNumericAndBranch(phi_, terminating, token); | 943 new(zone()) HCompareNumericAndBranch(phi_, terminating, token); |
923 compare->SetSuccessorAt(0, body_block_); | 944 compare->SetSuccessorAt(0, body_block_); |
924 compare->SetSuccessorAt(1, exit_block_); | 945 compare->SetSuccessorAt(1, exit_block_); |
925 builder_->current_block()->Finish(compare); | 946 builder_->current_block()->Finish(compare); |
926 | 947 |
927 builder_->set_current_block(body_block_); | 948 builder_->set_current_block(body_block_); |
928 if (direction_ == kPreIncrement || direction_ == kPreDecrement) { | 949 if (direction_ == kPreIncrement || direction_ == kPreDecrement) { |
929 HValue* one = builder_->graph()->GetConstant1(); | 950 HValue* one = builder_->graph()->GetConstant1(); |
930 if (direction_ == kPreIncrement) { | 951 if (direction_ == kPreIncrement) { |
931 increment_ = HAdd::New(zone(), context_, phi_, one); | 952 increment_ = HAdd::New(zone(), context_, phi_, one); |
932 } else { | 953 } else { |
933 increment_ = HSub::New(zone(), context_, phi_, one); | 954 increment_ = HSub::New(zone(), context_, phi_, one); |
934 } | 955 } |
935 increment_->ClearFlag(HValue::kCanOverflow); | 956 increment_->ClearFlag(HValue::kCanOverflow); |
936 builder_->AddInstruction(increment_); | 957 builder_->AddInstruction(increment_); |
937 return increment_; | 958 return increment_; |
938 } else { | 959 } else { |
939 return phi_; | 960 return phi_; |
940 } | 961 } |
941 } | 962 } |
942 | 963 |
943 | 964 |
| 965 void HGraphBuilder::LoopBuilder::Break() { |
| 966 if (exit_trampoline_block_ == NULL) { |
| 967 // Its the first time we saw a break. |
| 968 HEnvironment* env = exit_block_->last_environment()->Copy(); |
| 969 exit_trampoline_block_ = builder_->CreateBasicBlock(env); |
| 970 exit_block_->GotoNoSimulate(exit_trampoline_block_); |
| 971 } |
| 972 |
| 973 builder_->current_block()->GotoNoSimulate(exit_trampoline_block_); |
| 974 } |
| 975 |
| 976 |
944 void HGraphBuilder::LoopBuilder::EndBody() { | 977 void HGraphBuilder::LoopBuilder::EndBody() { |
945 ASSERT(!finished_); | 978 ASSERT(!finished_); |
946 | 979 |
947 if (direction_ == kPostIncrement || direction_ == kPostDecrement) { | 980 if (direction_ == kPostIncrement || direction_ == kPostDecrement) { |
948 HValue* one = builder_->graph()->GetConstant1(); | |
949 if (direction_ == kPostIncrement) { | 981 if (direction_ == kPostIncrement) { |
950 increment_ = HAdd::New(zone(), context_, phi_, one); | 982 increment_ = HAdd::New(zone(), context_, phi_, increment_amount_); |
951 } else { | 983 } else { |
952 increment_ = HSub::New(zone(), context_, phi_, one); | 984 increment_ = HSub::New(zone(), context_, phi_, increment_amount_); |
953 } | 985 } |
954 increment_->ClearFlag(HValue::kCanOverflow); | 986 increment_->ClearFlag(HValue::kCanOverflow); |
955 builder_->AddInstruction(increment_); | 987 builder_->AddInstruction(increment_); |
956 } | 988 } |
957 | 989 |
958 // Push the new increment value on the expression stack to merge into the phi. | 990 // Push the new increment value on the expression stack to merge into the phi. |
959 builder_->environment()->Push(increment_); | 991 builder_->environment()->Push(increment_); |
960 HBasicBlock* last_block = builder_->current_block(); | 992 HBasicBlock* last_block = builder_->current_block(); |
961 last_block->GotoNoSimulate(header_block_); | 993 last_block->GotoNoSimulate(header_block_); |
962 header_block_->loop_information()->RegisterBackEdge(last_block); | 994 header_block_->loop_information()->RegisterBackEdge(last_block); |
963 | 995 |
964 builder_->set_current_block(exit_block_); | 996 if (exit_trampoline_block_ != NULL) { |
965 // Pop the phi from the expression stack | 997 builder_->set_current_block(exit_trampoline_block_); |
966 builder_->environment()->Pop(); | 998 } else { |
| 999 builder_->set_current_block(exit_block_); |
| 1000 } |
967 finished_ = true; | 1001 finished_ = true; |
968 } | 1002 } |
969 | 1003 |
970 | 1004 |
971 HGraph* HGraphBuilder::CreateGraph() { | 1005 HGraph* HGraphBuilder::CreateGraph() { |
972 graph_ = new(zone()) HGraph(info_); | 1006 graph_ = new(zone()) HGraph(info_); |
973 if (FLAG_hydrogen_stats) isolate()->GetHStatistics()->Initialize(info_); | 1007 if (FLAG_hydrogen_stats) isolate()->GetHStatistics()->Initialize(info_); |
974 CompilationPhase phase("H_Block building", info_); | 1008 CompilationPhase phase("H_Block building", info_); |
975 set_current_block(graph()->entry_block()); | 1009 set_current_block(graph()->entry_block()); |
976 if (!BuildGraph()) return NULL; | 1010 if (!BuildGraph()) return NULL; |
(...skipping 8730 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
9707 if (ShouldProduceTraceOutput()) { | 9741 if (ShouldProduceTraceOutput()) { |
9708 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); | 9742 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); |
9709 } | 9743 } |
9710 | 9744 |
9711 #ifdef DEBUG | 9745 #ifdef DEBUG |
9712 graph_->Verify(false); // No full verify. | 9746 graph_->Verify(false); // No full verify. |
9713 #endif | 9747 #endif |
9714 } | 9748 } |
9715 | 9749 |
9716 } } // namespace v8::internal | 9750 } } // namespace v8::internal |
OLD | NEW |