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

Side by Side Diff: src/hydrogen.cc

Issue 10831172: Introduced TypeFeedbackId and BailoutId types. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Incorporated review feedback. Created 8 years, 4 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 | Annotate | Revision Log
« no previous file with comments | « src/hydrogen.h ('k') | src/hydrogen-instructions.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 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 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
126 HDeoptimize* instr = new(zone()) HDeoptimize(environment->length(), zone()); 126 HDeoptimize* instr = new(zone()) HDeoptimize(environment->length(), zone());
127 for (int i = 0; i < environment->length(); i++) { 127 for (int i = 0; i < environment->length(); i++) {
128 HValue* val = environment->values()->at(i); 128 HValue* val = environment->values()->at(i);
129 instr->AddEnvironmentValue(val, zone()); 129 instr->AddEnvironmentValue(val, zone());
130 } 130 }
131 131
132 return instr; 132 return instr;
133 } 133 }
134 134
135 135
136 HSimulate* HBasicBlock::CreateSimulate(int ast_id) { 136 HSimulate* HBasicBlock::CreateSimulate(BailoutId ast_id) {
137 ASSERT(HasEnvironment()); 137 ASSERT(HasEnvironment());
138 HEnvironment* environment = last_environment(); 138 HEnvironment* environment = last_environment();
139 ASSERT(ast_id == AstNode::kNoNumber || 139 ASSERT(ast_id.IsNone() ||
140 environment->closure()->shared()->VerifyBailoutId(ast_id)); 140 environment->closure()->shared()->VerifyBailoutId(ast_id));
141 141
142 int push_count = environment->push_count(); 142 int push_count = environment->push_count();
143 int pop_count = environment->pop_count(); 143 int pop_count = environment->pop_count();
144 144
145 HSimulate* instr = new(zone()) HSimulate(ast_id, pop_count, zone()); 145 HSimulate* instr = new(zone()) HSimulate(ast_id, pop_count, zone());
146 for (int i = push_count - 1; i >= 0; --i) { 146 for (int i = push_count - 1; i >= 0; --i) {
147 instr->AddPushedValue(environment->ExpressionStackAt(i)); 147 instr->AddPushedValue(environment->ExpressionStackAt(i));
148 } 148 }
149 for (int i = 0; i < environment->assigned_variables()->length(); ++i) { 149 for (int i = 0; i < environment->assigned_variables()->length(); ++i) {
(...skipping 17 matching lines...) Expand all
167 167
168 void HBasicBlock::Goto(HBasicBlock* block, FunctionState* state) { 168 void HBasicBlock::Goto(HBasicBlock* block, FunctionState* state) {
169 bool drop_extra = state != NULL && state->drop_extra(); 169 bool drop_extra = state != NULL && state->drop_extra();
170 bool arguments_pushed = state != NULL && state->arguments_pushed(); 170 bool arguments_pushed = state != NULL && state->arguments_pushed();
171 171
172 if (block->IsInlineReturnTarget()) { 172 if (block->IsInlineReturnTarget()) {
173 AddInstruction(new(zone()) HLeaveInlined(arguments_pushed)); 173 AddInstruction(new(zone()) HLeaveInlined(arguments_pushed));
174 last_environment_ = last_environment()->DiscardInlined(drop_extra); 174 last_environment_ = last_environment()->DiscardInlined(drop_extra);
175 } 175 }
176 176
177 AddSimulate(AstNode::kNoNumber); 177 AddSimulate(BailoutId::None());
178 HGoto* instr = new(zone()) HGoto(block); 178 HGoto* instr = new(zone()) HGoto(block);
179 Finish(instr); 179 Finish(instr);
180 } 180 }
181 181
182 182
183 void HBasicBlock::AddLeaveInlined(HValue* return_value, 183 void HBasicBlock::AddLeaveInlined(HValue* return_value,
184 HBasicBlock* target, 184 HBasicBlock* target,
185 FunctionState* state) { 185 FunctionState* state) {
186 bool drop_extra = state != NULL && state->drop_extra(); 186 bool drop_extra = state != NULL && state->drop_extra();
187 bool arguments_pushed = state != NULL && state->arguments_pushed(); 187 bool arguments_pushed = state != NULL && state->arguments_pushed();
188 188
189 ASSERT(target->IsInlineReturnTarget()); 189 ASSERT(target->IsInlineReturnTarget());
190 ASSERT(return_value != NULL); 190 ASSERT(return_value != NULL);
191 AddInstruction(new(zone()) HLeaveInlined(arguments_pushed)); 191 AddInstruction(new(zone()) HLeaveInlined(arguments_pushed));
192 last_environment_ = last_environment()->DiscardInlined(drop_extra); 192 last_environment_ = last_environment()->DiscardInlined(drop_extra);
193 last_environment()->Push(return_value); 193 last_environment()->Push(return_value);
194 AddSimulate(AstNode::kNoNumber); 194 AddSimulate(BailoutId::None());
195 HGoto* instr = new(zone()) HGoto(target); 195 HGoto* instr = new(zone()) HGoto(target);
196 Finish(instr); 196 Finish(instr);
197 } 197 }
198 198
199 199
200 void HBasicBlock::SetInitialEnvironment(HEnvironment* env) { 200 void HBasicBlock::SetInitialEnvironment(HEnvironment* env) {
201 ASSERT(!HasEnvironment()); 201 ASSERT(!HasEnvironment());
202 ASSERT(first() == NULL); 202 ASSERT(first() == NULL);
203 UpdateEnvironment(env); 203 UpdateEnvironment(env);
204 } 204 }
205 205
206 206
207 void HBasicBlock::SetJoinId(int ast_id) { 207 void HBasicBlock::SetJoinId(BailoutId ast_id) {
208 int length = predecessors_.length(); 208 int length = predecessors_.length();
209 ASSERT(length > 0); 209 ASSERT(length > 0);
210 for (int i = 0; i < length; i++) { 210 for (int i = 0; i < length; i++) {
211 HBasicBlock* predecessor = predecessors_[i]; 211 HBasicBlock* predecessor = predecessors_[i];
212 ASSERT(predecessor->end()->IsGoto()); 212 ASSERT(predecessor->end()->IsGoto());
213 HSimulate* simulate = HSimulate::cast(predecessor->end()->previous()); 213 HSimulate* simulate = HSimulate::cast(predecessor->end()->previous());
214 // We only need to verify the ID once. 214 // We only need to verify the ID once.
215 ASSERT(i != 0 || 215 ASSERT(i != 0 ||
216 predecessor->last_environment()->closure()->shared() 216 predecessor->last_environment()->closure()->shared()
217 ->VerifyBailoutId(ast_id)); 217 ->VerifyBailoutId(ast_id));
(...skipping 302 matching lines...) Expand 10 before | Expand all | Expand 10 after
520 520
521 // Check that phis have correct arguments. 521 // Check that phis have correct arguments.
522 for (int j = 0; j < block->phis()->length(); j++) { 522 for (int j = 0; j < block->phis()->length(); j++) {
523 HPhi* phi = block->phis()->at(j); 523 HPhi* phi = block->phis()->at(j);
524 phi->Verify(); 524 phi->Verify();
525 } 525 }
526 526
527 // Check that all join blocks have predecessors that end with an 527 // Check that all join blocks have predecessors that end with an
528 // unconditional goto and agree on their environment node id. 528 // unconditional goto and agree on their environment node id.
529 if (block->predecessors()->length() >= 2) { 529 if (block->predecessors()->length() >= 2) {
530 int id = block->predecessors()->first()->last_environment()->ast_id(); 530 BailoutId id =
531 block->predecessors()->first()->last_environment()->ast_id();
531 for (int k = 0; k < block->predecessors()->length(); k++) { 532 for (int k = 0; k < block->predecessors()->length(); k++) {
532 HBasicBlock* predecessor = block->predecessors()->at(k); 533 HBasicBlock* predecessor = block->predecessors()->at(k);
533 ASSERT(predecessor->end()->IsGoto()); 534 ASSERT(predecessor->end()->IsGoto());
534 ASSERT(predecessor->last_environment()->ast_id() == id); 535 ASSERT(predecessor->last_environment()->ast_id() == id);
535 } 536 }
536 } 537 }
537 } 538 }
538 539
539 // Check special property of first block to have no predecessors. 540 // Check special property of first block to have no predecessors.
540 ASSERT(blocks_.at(0)->predecessors()->is_empty()); 541 ASSERT(blocks_.at(0)->predecessors()->is_empty());
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after
629 zone_(info->zone()), 630 zone_(info->zone()),
630 inline_bailout_(false) { 631 inline_bailout_(false) {
631 // This is not initialized in the initializer list because the 632 // This is not initialized in the initializer list because the
632 // constructor for the initial state relies on function_state_ == NULL 633 // constructor for the initial state relies on function_state_ == NULL
633 // to know it's the initial state. 634 // to know it's the initial state.
634 function_state_= &initial_function_state_; 635 function_state_= &initial_function_state_;
635 } 636 }
636 637
637 HBasicBlock* HGraphBuilder::CreateJoin(HBasicBlock* first, 638 HBasicBlock* HGraphBuilder::CreateJoin(HBasicBlock* first,
638 HBasicBlock* second, 639 HBasicBlock* second,
639 int join_id) { 640 BailoutId join_id) {
640 if (first == NULL) { 641 if (first == NULL) {
641 return second; 642 return second;
642 } else if (second == NULL) { 643 } else if (second == NULL) {
643 return first; 644 return first;
644 } else { 645 } else {
645 HBasicBlock* join_block = graph_->CreateBasicBlock(); 646 HBasicBlock* join_block = graph_->CreateBasicBlock();
646 first->Goto(join_block); 647 first->Goto(join_block);
647 second->Goto(join_block); 648 second->Goto(join_block);
648 join_block->SetJoinId(join_id); 649 join_block->SetJoinId(join_id);
649 return join_block; 650 return join_block;
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
690 next_block_id_(0), 691 next_block_id_(0),
691 entry_block_(NULL), 692 entry_block_(NULL),
692 blocks_(8, info->zone()), 693 blocks_(8, info->zone()),
693 values_(16, info->zone()), 694 values_(16, info->zone()),
694 phi_list_(NULL), 695 phi_list_(NULL),
695 info_(info), 696 info_(info),
696 zone_(info->zone()), 697 zone_(info->zone()),
697 is_recursive_(false) { 698 is_recursive_(false) {
698 start_environment_ = 699 start_environment_ =
699 new(zone_) HEnvironment(NULL, info->scope(), info->closure(), zone_); 700 new(zone_) HEnvironment(NULL, info->scope(), info->closure(), zone_);
700 start_environment_->set_ast_id(AstNode::kFunctionEntryId); 701 start_environment_->set_ast_id(BailoutId::FunctionEntry());
701 entry_block_ = CreateBasicBlock(); 702 entry_block_ = CreateBasicBlock();
702 entry_block_->SetInitialEnvironment(start_environment_); 703 entry_block_->SetInitialEnvironment(start_environment_);
703 } 704 }
704 705
705 706
706 HBasicBlock* HGraph::CreateBasicBlock() { 707 HBasicBlock* HGraph::CreateBasicBlock() {
707 HBasicBlock* result = new(zone()) HBasicBlock(this); 708 HBasicBlock* result = new(zone()) HBasicBlock(this);
708 blocks_.Add(result, zone()); 709 blocks_.Add(result, zone());
709 return result; 710 return result;
710 } 711 }
(...skipping 2124 matching lines...) Expand 10 before | Expand all | Expand 10 after
2835 } 2836 }
2836 owner()->Push(value); 2837 owner()->Push(value);
2837 } 2838 }
2838 2839
2839 2840
2840 void TestContext::ReturnValue(HValue* value) { 2841 void TestContext::ReturnValue(HValue* value) {
2841 BuildBranch(value); 2842 BuildBranch(value);
2842 } 2843 }
2843 2844
2844 2845
2845 void EffectContext::ReturnInstruction(HInstruction* instr, int ast_id) { 2846 void EffectContext::ReturnInstruction(HInstruction* instr, BailoutId ast_id) {
2846 ASSERT(!instr->IsControlInstruction()); 2847 ASSERT(!instr->IsControlInstruction());
2847 owner()->AddInstruction(instr); 2848 owner()->AddInstruction(instr);
2848 if (instr->HasObservableSideEffects()) owner()->AddSimulate(ast_id); 2849 if (instr->HasObservableSideEffects()) owner()->AddSimulate(ast_id);
2849 } 2850 }
2850 2851
2851 2852
2852 void EffectContext::ReturnControl(HControlInstruction* instr, int ast_id) { 2853 void EffectContext::ReturnControl(HControlInstruction* instr,
2854 BailoutId ast_id) {
2853 ASSERT(!instr->HasObservableSideEffects()); 2855 ASSERT(!instr->HasObservableSideEffects());
2854 HBasicBlock* empty_true = owner()->graph()->CreateBasicBlock(); 2856 HBasicBlock* empty_true = owner()->graph()->CreateBasicBlock();
2855 HBasicBlock* empty_false = owner()->graph()->CreateBasicBlock(); 2857 HBasicBlock* empty_false = owner()->graph()->CreateBasicBlock();
2856 instr->SetSuccessorAt(0, empty_true); 2858 instr->SetSuccessorAt(0, empty_true);
2857 instr->SetSuccessorAt(1, empty_false); 2859 instr->SetSuccessorAt(1, empty_false);
2858 owner()->current_block()->Finish(instr); 2860 owner()->current_block()->Finish(instr);
2859 HBasicBlock* join = owner()->CreateJoin(empty_true, empty_false, ast_id); 2861 HBasicBlock* join = owner()->CreateJoin(empty_true, empty_false, ast_id);
2860 owner()->set_current_block(join); 2862 owner()->set_current_block(join);
2861 } 2863 }
2862 2864
2863 2865
2864 void ValueContext::ReturnInstruction(HInstruction* instr, int ast_id) { 2866 void ValueContext::ReturnInstruction(HInstruction* instr, BailoutId ast_id) {
2865 ASSERT(!instr->IsControlInstruction()); 2867 ASSERT(!instr->IsControlInstruction());
2866 if (!arguments_allowed() && instr->CheckFlag(HValue::kIsArguments)) { 2868 if (!arguments_allowed() && instr->CheckFlag(HValue::kIsArguments)) {
2867 return owner()->Bailout("bad value context for arguments object value"); 2869 return owner()->Bailout("bad value context for arguments object value");
2868 } 2870 }
2869 owner()->AddInstruction(instr); 2871 owner()->AddInstruction(instr);
2870 owner()->Push(instr); 2872 owner()->Push(instr);
2871 if (instr->HasObservableSideEffects()) owner()->AddSimulate(ast_id); 2873 if (instr->HasObservableSideEffects()) owner()->AddSimulate(ast_id);
2872 } 2874 }
2873 2875
2874 2876
2875 void ValueContext::ReturnControl(HControlInstruction* instr, int ast_id) { 2877 void ValueContext::ReturnControl(HControlInstruction* instr, BailoutId ast_id) {
2876 ASSERT(!instr->HasObservableSideEffects()); 2878 ASSERT(!instr->HasObservableSideEffects());
2877 if (!arguments_allowed() && instr->CheckFlag(HValue::kIsArguments)) { 2879 if (!arguments_allowed() && instr->CheckFlag(HValue::kIsArguments)) {
2878 return owner()->Bailout("bad value context for arguments object value"); 2880 return owner()->Bailout("bad value context for arguments object value");
2879 } 2881 }
2880 HBasicBlock* materialize_false = owner()->graph()->CreateBasicBlock(); 2882 HBasicBlock* materialize_false = owner()->graph()->CreateBasicBlock();
2881 HBasicBlock* materialize_true = owner()->graph()->CreateBasicBlock(); 2883 HBasicBlock* materialize_true = owner()->graph()->CreateBasicBlock();
2882 instr->SetSuccessorAt(0, materialize_true); 2884 instr->SetSuccessorAt(0, materialize_true);
2883 instr->SetSuccessorAt(1, materialize_false); 2885 instr->SetSuccessorAt(1, materialize_false);
2884 owner()->current_block()->Finish(instr); 2886 owner()->current_block()->Finish(instr);
2885 owner()->set_current_block(materialize_true); 2887 owner()->set_current_block(materialize_true);
2886 owner()->Push(owner()->graph()->GetConstantTrue()); 2888 owner()->Push(owner()->graph()->GetConstantTrue());
2887 owner()->set_current_block(materialize_false); 2889 owner()->set_current_block(materialize_false);
2888 owner()->Push(owner()->graph()->GetConstantFalse()); 2890 owner()->Push(owner()->graph()->GetConstantFalse());
2889 HBasicBlock* join = 2891 HBasicBlock* join =
2890 owner()->CreateJoin(materialize_true, materialize_false, ast_id); 2892 owner()->CreateJoin(materialize_true, materialize_false, ast_id);
2891 owner()->set_current_block(join); 2893 owner()->set_current_block(join);
2892 } 2894 }
2893 2895
2894 2896
2895 void TestContext::ReturnInstruction(HInstruction* instr, int ast_id) { 2897 void TestContext::ReturnInstruction(HInstruction* instr, BailoutId ast_id) {
2896 ASSERT(!instr->IsControlInstruction()); 2898 ASSERT(!instr->IsControlInstruction());
2897 HGraphBuilder* builder = owner(); 2899 HGraphBuilder* builder = owner();
2898 builder->AddInstruction(instr); 2900 builder->AddInstruction(instr);
2899 // We expect a simulate after every expression with side effects, though 2901 // We expect a simulate after every expression with side effects, though
2900 // this one isn't actually needed (and wouldn't work if it were targeted). 2902 // this one isn't actually needed (and wouldn't work if it were targeted).
2901 if (instr->HasObservableSideEffects()) { 2903 if (instr->HasObservableSideEffects()) {
2902 builder->Push(instr); 2904 builder->Push(instr);
2903 builder->AddSimulate(ast_id); 2905 builder->AddSimulate(ast_id);
2904 builder->Pop(); 2906 builder->Pop();
2905 } 2907 }
2906 BuildBranch(instr); 2908 BuildBranch(instr);
2907 } 2909 }
2908 2910
2909 2911
2910 void TestContext::ReturnControl(HControlInstruction* instr, int ast_id) { 2912 void TestContext::ReturnControl(HControlInstruction* instr, BailoutId ast_id) {
2911 ASSERT(!instr->HasObservableSideEffects()); 2913 ASSERT(!instr->HasObservableSideEffects());
2912 HBasicBlock* empty_true = owner()->graph()->CreateBasicBlock(); 2914 HBasicBlock* empty_true = owner()->graph()->CreateBasicBlock();
2913 HBasicBlock* empty_false = owner()->graph()->CreateBasicBlock(); 2915 HBasicBlock* empty_false = owner()->graph()->CreateBasicBlock();
2914 instr->SetSuccessorAt(0, empty_true); 2916 instr->SetSuccessorAt(0, empty_true);
2915 instr->SetSuccessorAt(1, empty_false); 2917 instr->SetSuccessorAt(1, empty_false);
2916 owner()->current_block()->Finish(instr); 2918 owner()->current_block()->Finish(instr);
2917 empty_true->Goto(if_true(), owner()->function_state()); 2919 empty_true->Goto(if_true(), owner()->function_state());
2918 empty_false->Goto(if_false(), owner()->function_state()); 2920 empty_false->Goto(if_false(), owner()->function_state());
2919 owner()->set_current_block(NULL); 2921 owner()->set_current_block(NULL);
2920 } 2922 }
2921 2923
2922 2924
2923 void TestContext::BuildBranch(HValue* value) { 2925 void TestContext::BuildBranch(HValue* value) {
2924 // We expect the graph to be in edge-split form: there is no edge that 2926 // We expect the graph to be in edge-split form: there is no edge that
2925 // connects a branch node to a join node. We conservatively ensure that 2927 // connects a branch node to a join node. We conservatively ensure that
2926 // property by always adding an empty block on the outgoing edges of this 2928 // property by always adding an empty block on the outgoing edges of this
2927 // branch. 2929 // branch.
2928 HGraphBuilder* builder = owner(); 2930 HGraphBuilder* builder = owner();
2929 if (value != NULL && value->CheckFlag(HValue::kIsArguments)) { 2931 if (value != NULL && value->CheckFlag(HValue::kIsArguments)) {
2930 builder->Bailout("arguments object value in a test context"); 2932 builder->Bailout("arguments object value in a test context");
2931 } 2933 }
2932 HBasicBlock* empty_true = builder->graph()->CreateBasicBlock(); 2934 HBasicBlock* empty_true = builder->graph()->CreateBasicBlock();
2933 HBasicBlock* empty_false = builder->graph()->CreateBasicBlock(); 2935 HBasicBlock* empty_false = builder->graph()->CreateBasicBlock();
2934 unsigned test_id = condition()->test_id(); 2936 TypeFeedbackId test_id = condition()->test_id();
2935 ToBooleanStub::Types expected(builder->oracle()->ToBooleanTypes(test_id)); 2937 ToBooleanStub::Types expected(builder->oracle()->ToBooleanTypes(test_id));
2936 HBranch* test = new(zone()) HBranch(value, empty_true, empty_false, expected); 2938 HBranch* test = new(zone()) HBranch(value, empty_true, empty_false, expected);
2937 builder->current_block()->Finish(test); 2939 builder->current_block()->Finish(test);
2938 2940
2939 empty_true->Goto(if_true(), owner()->function_state()); 2941 empty_true->Goto(if_true(), owner()->function_state());
2940 empty_false->Goto(if_false(), owner()->function_state()); 2942 empty_false->Goto(if_false(), owner()->function_state());
2941 builder->set_current_block(NULL); 2943 builder->set_current_block(NULL);
2942 } 2944 }
2943 2945
2944 2946
(...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after
3045 // block in HInstruction::InsertAfter) seals the start block from 3047 // block in HInstruction::InsertAfter) seals the start block from
3046 // getting unwanted instructions inserted. 3048 // getting unwanted instructions inserted.
3047 // 3049 //
3048 // TODO(kmillikin): Fix this. Stop mutating the initial environment. 3050 // TODO(kmillikin): Fix this. Stop mutating the initial environment.
3049 // Make the Hydrogen instructions in the initial block into Hydrogen 3051 // Make the Hydrogen instructions in the initial block into Hydrogen
3050 // values (but not instructions), present in the initial environment and 3052 // values (but not instructions), present in the initial environment and
3051 // not replayed by the Lithium translation. 3053 // not replayed by the Lithium translation.
3052 HEnvironment* initial_env = environment()->CopyWithoutHistory(); 3054 HEnvironment* initial_env = environment()->CopyWithoutHistory();
3053 HBasicBlock* body_entry = CreateBasicBlock(initial_env); 3055 HBasicBlock* body_entry = CreateBasicBlock(initial_env);
3054 current_block()->Goto(body_entry); 3056 current_block()->Goto(body_entry);
3055 body_entry->SetJoinId(AstNode::kFunctionEntryId); 3057 body_entry->SetJoinId(BailoutId::FunctionEntry());
3056 set_current_block(body_entry); 3058 set_current_block(body_entry);
3057 3059
3058 // Handle implicit declaration of the function name in named function 3060 // Handle implicit declaration of the function name in named function
3059 // expressions before other declarations. 3061 // expressions before other declarations.
3060 if (scope->is_function_scope() && scope->function() != NULL) { 3062 if (scope->is_function_scope() && scope->function() != NULL) {
3061 VisitVariableDeclaration(scope->function()); 3063 VisitVariableDeclaration(scope->function());
3062 } 3064 }
3063 VisitDeclarations(scope->declarations()); 3065 VisitDeclarations(scope->declarations());
3064 AddSimulate(AstNode::kDeclarationsId); 3066 AddSimulate(BailoutId::Declarations());
3065 3067
3066 HValue* context = environment()->LookupContext(); 3068 HValue* context = environment()->LookupContext();
3067 AddInstruction( 3069 AddInstruction(
3068 new(zone()) HStackCheck(context, HStackCheck::kFunctionEntry)); 3070 new(zone()) HStackCheck(context, HStackCheck::kFunctionEntry));
3069 3071
3070 VisitStatements(info()->function()->body()); 3072 VisitStatements(info()->function()->body());
3071 if (HasStackOverflow()) return NULL; 3073 if (HasStackOverflow()) return NULL;
3072 3074
3073 if (current_block() != NULL) { 3075 if (current_block() != NULL) {
3074 HReturn* instr = new(zone()) HReturn(graph()->GetConstantUndefined()); 3076 HReturn* instr = new(zone()) HReturn(graph()->GetConstantUndefined());
(...skipping 495 matching lines...) Expand 10 before | Expand all | Expand 10 after
3570 } 3572 }
3571 3573
3572 3574
3573 HInstruction* HGraphBuilder::AddInstruction(HInstruction* instr) { 3575 HInstruction* HGraphBuilder::AddInstruction(HInstruction* instr) {
3574 ASSERT(current_block() != NULL); 3576 ASSERT(current_block() != NULL);
3575 current_block()->AddInstruction(instr); 3577 current_block()->AddInstruction(instr);
3576 return instr; 3578 return instr;
3577 } 3579 }
3578 3580
3579 3581
3580 void HGraphBuilder::AddSimulate(int ast_id) { 3582 void HGraphBuilder::AddSimulate(BailoutId ast_id) {
3581 ASSERT(current_block() != NULL); 3583 ASSERT(current_block() != NULL);
3582 current_block()->AddSimulate(ast_id); 3584 current_block()->AddSimulate(ast_id);
3583 } 3585 }
3584 3586
3585 3587
3586 void HGraphBuilder::AddPhi(HPhi* instr) { 3588 void HGraphBuilder::AddPhi(HPhi* instr) {
3587 ASSERT(current_block() != NULL); 3589 ASSERT(current_block() != NULL);
3588 current_block()->AddPhi(instr); 3590 current_block()->AddPhi(instr);
3589 } 3591 }
3590 3592
(...skipping 353 matching lines...) Expand 10 before | Expand all | Expand 10 after
3944 not_string_block = graph()->CreateBasicBlock(); 3946 not_string_block = graph()->CreateBasicBlock();
3945 3947
3946 string_check->SetSuccessorAt(0, first_test_block); 3948 string_check->SetSuccessorAt(0, first_test_block);
3947 string_check->SetSuccessorAt(1, not_string_block); 3949 string_check->SetSuccessorAt(1, not_string_block);
3948 current_block()->Finish(string_check); 3950 current_block()->Finish(string_check);
3949 3951
3950 set_current_block(first_test_block); 3952 set_current_block(first_test_block);
3951 } 3953 }
3952 3954
3953 // 2. Build all the tests, with dangling true branches 3955 // 2. Build all the tests, with dangling true branches
3954 int default_id = AstNode::kNoNumber; 3956 BailoutId default_id = BailoutId::None();
3955 for (int i = 0; i < clause_count; ++i) { 3957 for (int i = 0; i < clause_count; ++i) {
3956 CaseClause* clause = clauses->at(i); 3958 CaseClause* clause = clauses->at(i);
3957 if (clause->is_default()) { 3959 if (clause->is_default()) {
3958 default_id = clause->EntryId(); 3960 default_id = clause->EntryId();
3959 continue; 3961 continue;
3960 } 3962 }
3961 if (switch_type == SMI_SWITCH) { 3963 if (switch_type == SMI_SWITCH) {
3962 clause->RecordTypeFeedback(oracle()); 3964 clause->RecordTypeFeedback(oracle());
3963 } 3965 }
3964 3966
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
3997 current_block()->Finish(compare); 3999 current_block()->Finish(compare);
3998 4000
3999 set_current_block(next_test_block); 4001 set_current_block(next_test_block);
4000 } 4002 }
4001 4003
4002 // Save the current block to use for the default or to join with the 4004 // Save the current block to use for the default or to join with the
4003 // exit. This block is NULL if we deoptimized. 4005 // exit. This block is NULL if we deoptimized.
4004 HBasicBlock* last_block = current_block(); 4006 HBasicBlock* last_block = current_block();
4005 4007
4006 if (not_string_block != NULL) { 4008 if (not_string_block != NULL) {
4007 int join_id = (default_id != AstNode::kNoNumber) 4009 BailoutId join_id = !default_id.IsNone() ? default_id : stmt->ExitId();
4008 ? default_id
4009 : stmt->ExitId();
4010 last_block = CreateJoin(last_block, not_string_block, join_id); 4010 last_block = CreateJoin(last_block, not_string_block, join_id);
4011 } 4011 }
4012 4012
4013 // 3. Loop over the clauses and the linked list of tests in lockstep, 4013 // 3. Loop over the clauses and the linked list of tests in lockstep,
4014 // translating the clause bodies. 4014 // translating the clause bodies.
4015 HBasicBlock* curr_test_block = first_test_block; 4015 HBasicBlock* curr_test_block = first_test_block;
4016 HBasicBlock* fall_through_block = NULL; 4016 HBasicBlock* fall_through_block = NULL;
4017 4017
4018 BreakAndContinueInfo break_info(stmt); 4018 BreakAndContinueInfo break_info(stmt);
4019 { BreakAndContinueScope push(&break_info, this); 4019 { BreakAndContinueScope push(&break_info, this);
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
4089 HBasicBlock* non_osr_entry = graph()->CreateBasicBlock(); 4089 HBasicBlock* non_osr_entry = graph()->CreateBasicBlock();
4090 HBasicBlock* osr_entry = graph()->CreateBasicBlock(); 4090 HBasicBlock* osr_entry = graph()->CreateBasicBlock();
4091 HValue* true_value = graph()->GetConstantTrue(); 4091 HValue* true_value = graph()->GetConstantTrue();
4092 HBranch* test = new(zone()) HBranch(true_value, non_osr_entry, osr_entry); 4092 HBranch* test = new(zone()) HBranch(true_value, non_osr_entry, osr_entry);
4093 current_block()->Finish(test); 4093 current_block()->Finish(test);
4094 4094
4095 HBasicBlock* loop_predecessor = graph()->CreateBasicBlock(); 4095 HBasicBlock* loop_predecessor = graph()->CreateBasicBlock();
4096 non_osr_entry->Goto(loop_predecessor); 4096 non_osr_entry->Goto(loop_predecessor);
4097 4097
4098 set_current_block(osr_entry); 4098 set_current_block(osr_entry);
4099 int osr_entry_id = statement->OsrEntryId(); 4099 BailoutId osr_entry_id = statement->OsrEntryId();
4100 int first_expression_index = environment()->first_expression_index(); 4100 int first_expression_index = environment()->first_expression_index();
4101 int length = environment()->length(); 4101 int length = environment()->length();
4102 ZoneList<HUnknownOSRValue*>* osr_values = 4102 ZoneList<HUnknownOSRValue*>* osr_values =
4103 new(zone()) ZoneList<HUnknownOSRValue*>(length, zone()); 4103 new(zone()) ZoneList<HUnknownOSRValue*>(length, zone());
4104 4104
4105 for (int i = 0; i < first_expression_index; ++i) { 4105 for (int i = 0; i < first_expression_index; ++i) {
4106 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue; 4106 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue;
4107 AddInstruction(osr_value); 4107 AddInstruction(osr_value);
4108 environment()->Bind(i, osr_value); 4108 environment()->Bind(i, osr_value);
4109 osr_values->Add(osr_value, zone()); 4109 osr_values->Add(osr_value, zone());
(...skipping 1153 matching lines...) Expand 10 before | Expand all | Expand 10 after
5263 } 5263 }
5264 } 5264 }
5265 5265
5266 5266
5267 // Because not every expression has a position and there is not common 5267 // Because not every expression has a position and there is not common
5268 // superclass of Assignment and CountOperation, we cannot just pass the 5268 // superclass of Assignment and CountOperation, we cannot just pass the
5269 // owning expression instead of position and ast_id separately. 5269 // owning expression instead of position and ast_id separately.
5270 void HGraphBuilder::HandleGlobalVariableAssignment(Variable* var, 5270 void HGraphBuilder::HandleGlobalVariableAssignment(Variable* var,
5271 HValue* value, 5271 HValue* value,
5272 int position, 5272 int position,
5273 int ast_id) { 5273 BailoutId ast_id) {
5274 LookupResult lookup(isolate()); 5274 LookupResult lookup(isolate());
5275 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, true); 5275 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, true);
5276 if (type == kUseCell) { 5276 if (type == kUseCell) {
5277 Handle<GlobalObject> global(info()->global_object()); 5277 Handle<GlobalObject> global(info()->global_object());
5278 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup)); 5278 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
5279 HInstruction* instr = 5279 HInstruction* instr =
5280 new(zone()) HStoreGlobalCell(value, cell, lookup.GetPropertyDetails()); 5280 new(zone()) HStoreGlobalCell(value, cell, lookup.GetPropertyDetails());
5281 instr->set_position(position); 5281 instr->set_position(position);
5282 AddInstruction(instr); 5282 AddInstruction(instr);
5283 if (instr->HasObservableSideEffects()) AddSimulate(ast_id); 5283 if (instr->HasObservableSideEffects()) AddSimulate(ast_id);
(...skipping 675 matching lines...) Expand 10 before | Expand all | Expand 10 after
5959 HInstruction* instr = BuildUncheckedMonomorphicElementAccess( 5959 HInstruction* instr = BuildUncheckedMonomorphicElementAccess(
5960 object, key, val, check_maps, most_general_consolidated_map, false); 5960 object, key, val, check_maps, most_general_consolidated_map, false);
5961 return instr; 5961 return instr;
5962 } 5962 }
5963 5963
5964 5964
5965 HValue* HGraphBuilder::HandlePolymorphicElementAccess(HValue* object, 5965 HValue* HGraphBuilder::HandlePolymorphicElementAccess(HValue* object,
5966 HValue* key, 5966 HValue* key,
5967 HValue* val, 5967 HValue* val,
5968 Expression* prop, 5968 Expression* prop,
5969 int ast_id, 5969 BailoutId ast_id,
5970 int position, 5970 int position,
5971 bool is_store, 5971 bool is_store,
5972 bool* has_side_effects) { 5972 bool* has_side_effects) {
5973 *has_side_effects = false; 5973 *has_side_effects = false;
5974 AddInstruction(new(zone()) HCheckNonSmi(object)); 5974 AddInstruction(new(zone()) HCheckNonSmi(object));
5975 SmallMapList* maps = prop->GetReceiverTypes(); 5975 SmallMapList* maps = prop->GetReceiverTypes();
5976 bool todo_external_array = false; 5976 bool todo_external_array = false;
5977 5977
5978 if (!is_store) { 5978 if (!is_store) {
5979 HInstruction* consolidated_load = 5979 HInstruction* consolidated_load =
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after
6170 join->SetJoinId(ast_id); 6170 join->SetJoinId(ast_id);
6171 set_current_block(join); 6171 set_current_block(join);
6172 return is_store ? NULL : Pop(); 6172 return is_store ? NULL : Pop();
6173 } 6173 }
6174 6174
6175 6175
6176 HValue* HGraphBuilder::HandleKeyedElementAccess(HValue* obj, 6176 HValue* HGraphBuilder::HandleKeyedElementAccess(HValue* obj,
6177 HValue* key, 6177 HValue* key,
6178 HValue* val, 6178 HValue* val,
6179 Expression* expr, 6179 Expression* expr,
6180 int ast_id, 6180 BailoutId ast_id,
6181 int position, 6181 int position,
6182 bool is_store, 6182 bool is_store,
6183 bool* has_side_effects) { 6183 bool* has_side_effects) {
6184 ASSERT(!expr->IsPropertyName()); 6184 ASSERT(!expr->IsPropertyName());
6185 HInstruction* instr = NULL; 6185 HInstruction* instr = NULL;
6186 if (expr->IsMonomorphic()) { 6186 if (expr->IsMonomorphic()) {
6187 Handle<Map> map = expr->GetMonomorphicReceiverType(); 6187 Handle<Map> map = expr->GetMonomorphicReceiverType();
6188 if (map->has_slow_elements_kind()) { 6188 if (map->has_slow_elements_kind()) {
6189 instr = is_store ? BuildStoreKeyedGeneric(obj, key, val) 6189 instr = is_store ? BuildStoreKeyedGeneric(obj, key, val)
6190 : BuildLoadKeyedGeneric(obj, key); 6190 : BuildLoadKeyedGeneric(obj, key);
(...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after
6602 6602
6603 int nodes_added = target_shared->ast_node_count(); 6603 int nodes_added = target_shared->ast_node_count();
6604 return nodes_added; 6604 return nodes_added;
6605 } 6605 }
6606 6606
6607 6607
6608 bool HGraphBuilder::TryInline(CallKind call_kind, 6608 bool HGraphBuilder::TryInline(CallKind call_kind,
6609 Handle<JSFunction> target, 6609 Handle<JSFunction> target,
6610 int arguments_count, 6610 int arguments_count,
6611 HValue* receiver, 6611 HValue* receiver,
6612 int ast_id, 6612 BailoutId ast_id,
6613 int return_id, 6613 BailoutId return_id,
6614 ReturnHandlingFlag return_handling) { 6614 ReturnHandlingFlag return_handling) {
6615 int nodes_added = InliningAstSize(target); 6615 int nodes_added = InliningAstSize(target);
6616 if (nodes_added == kNotInlinable) return false; 6616 if (nodes_added == kNotInlinable) return false;
6617 6617
6618 Handle<JSFunction> caller = info()->closure(); 6618 Handle<JSFunction> caller = info()->closure();
6619 6619
6620 if (nodes_added > Min(FLAG_max_inlined_nodes, kUnlimitedMaxInlinedNodes)) { 6620 if (nodes_added > Min(FLAG_max_inlined_nodes, kUnlimitedMaxInlinedNodes)) {
6621 TraceInline(target, caller, "target AST is too large [early]"); 6621 TraceInline(target, caller, "target AST is too large [early]");
6622 return false; 6622 return false;
6623 } 6623 }
(...skipping 1472 matching lines...) Expand 10 before | Expand all | Expand 10 after
8096 Visit(expr->right()); 8096 Visit(expr->right());
8097 } 8097 }
8098 8098
8099 } else if (ast_context()->IsValue()) { 8099 } else if (ast_context()->IsValue()) {
8100 CHECK_ALIVE(VisitForValue(expr->left())); 8100 CHECK_ALIVE(VisitForValue(expr->left()));
8101 ASSERT(current_block() != NULL); 8101 ASSERT(current_block() != NULL);
8102 8102
8103 // We need an extra block to maintain edge-split form. 8103 // We need an extra block to maintain edge-split form.
8104 HBasicBlock* empty_block = graph()->CreateBasicBlock(); 8104 HBasicBlock* empty_block = graph()->CreateBasicBlock();
8105 HBasicBlock* eval_right = graph()->CreateBasicBlock(); 8105 HBasicBlock* eval_right = graph()->CreateBasicBlock();
8106 unsigned test_id = expr->left()->test_id(); 8106 TypeFeedbackId test_id = expr->left()->test_id();
8107 ToBooleanStub::Types expected(oracle()->ToBooleanTypes(test_id)); 8107 ToBooleanStub::Types expected(oracle()->ToBooleanTypes(test_id));
8108 HBranch* test = is_logical_and 8108 HBranch* test = is_logical_and
8109 ? new(zone()) HBranch(Top(), eval_right, empty_block, expected) 8109 ? new(zone()) HBranch(Top(), eval_right, empty_block, expected)
8110 : new(zone()) HBranch(Top(), empty_block, eval_right, expected); 8110 : new(zone()) HBranch(Top(), empty_block, eval_right, expected);
8111 current_block()->Finish(test); 8111 current_block()->Finish(test);
8112 8112
8113 set_current_block(eval_right); 8113 set_current_block(eval_right);
8114 Drop(1); // Value of the left subexpression. 8114 Drop(1); // Value of the left subexpression.
8115 CHECK_BAILOUT(VisitForValue(expr->right())); 8115 CHECK_BAILOUT(VisitForValue(expr->right()));
8116 8116
(...skipping 965 matching lines...) Expand 10 before | Expand all | Expand 10 after
9082 : closure_(closure), 9082 : closure_(closure),
9083 values_(0, zone), 9083 values_(0, zone),
9084 assigned_variables_(4, zone), 9084 assigned_variables_(4, zone),
9085 frame_type_(JS_FUNCTION), 9085 frame_type_(JS_FUNCTION),
9086 parameter_count_(0), 9086 parameter_count_(0),
9087 specials_count_(1), 9087 specials_count_(1),
9088 local_count_(0), 9088 local_count_(0),
9089 outer_(outer), 9089 outer_(outer),
9090 pop_count_(0), 9090 pop_count_(0),
9091 push_count_(0), 9091 push_count_(0),
9092 ast_id_(AstNode::kNoNumber), 9092 ast_id_(BailoutId::None()),
9093 zone_(zone) { 9093 zone_(zone) {
9094 Initialize(scope->num_parameters() + 1, scope->num_stack_slots(), 0); 9094 Initialize(scope->num_parameters() + 1, scope->num_stack_slots(), 0);
9095 } 9095 }
9096 9096
9097 9097
9098 HEnvironment::HEnvironment(const HEnvironment* other, Zone* zone) 9098 HEnvironment::HEnvironment(const HEnvironment* other, Zone* zone)
9099 : values_(0, zone), 9099 : values_(0, zone),
9100 assigned_variables_(0, zone), 9100 assigned_variables_(0, zone),
9101 frame_type_(JS_FUNCTION), 9101 frame_type_(JS_FUNCTION),
9102 parameter_count_(0), 9102 parameter_count_(0),
(...skipping 15 matching lines...) Expand all
9118 Zone* zone) 9118 Zone* zone)
9119 : closure_(closure), 9119 : closure_(closure),
9120 values_(arguments, zone), 9120 values_(arguments, zone),
9121 assigned_variables_(0, zone), 9121 assigned_variables_(0, zone),
9122 frame_type_(frame_type), 9122 frame_type_(frame_type),
9123 parameter_count_(arguments), 9123 parameter_count_(arguments),
9124 local_count_(0), 9124 local_count_(0),
9125 outer_(outer), 9125 outer_(outer),
9126 pop_count_(0), 9126 pop_count_(0),
9127 push_count_(0), 9127 push_count_(0),
9128 ast_id_(AstNode::kNoNumber), 9128 ast_id_(BailoutId::None()),
9129 zone_(zone) { 9129 zone_(zone) {
9130 } 9130 }
9131 9131
9132 9132
9133 void HEnvironment::Initialize(int parameter_count, 9133 void HEnvironment::Initialize(int parameter_count,
9134 int local_count, 9134 int local_count,
9135 int stack_height) { 9135 int stack_height) {
9136 parameter_count_ = parameter_count; 9136 parameter_count_ = parameter_count;
9137 local_count_ = local_count; 9137 local_count_ = local_count;
9138 9138
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after
9310 // calls (instead of the global receiver). 9310 // calls (instead of the global receiver).
9311 if ((target->shared()->native() || !function->is_classic_mode()) && 9311 if ((target->shared()->native() || !function->is_classic_mode()) &&
9312 call_kind == CALL_AS_FUNCTION && !is_construct) { 9312 call_kind == CALL_AS_FUNCTION && !is_construct) {
9313 inner->SetValueAt(0, undefined); 9313 inner->SetValueAt(0, undefined);
9314 } 9314 }
9315 inner->SetValueAt(arity + 1, LookupContext()); 9315 inner->SetValueAt(arity + 1, LookupContext());
9316 for (int i = arity + 2; i < inner->length(); ++i) { 9316 for (int i = arity + 2; i < inner->length(); ++i) {
9317 inner->SetValueAt(i, undefined); 9317 inner->SetValueAt(i, undefined);
9318 } 9318 }
9319 9319
9320 inner->set_ast_id(AstNode::kFunctionEntryId); 9320 inner->set_ast_id(BailoutId::FunctionEntry());
9321 return inner; 9321 return inner;
9322 } 9322 }
9323 9323
9324 9324
9325 void HEnvironment::PrintTo(StringStream* stream) { 9325 void HEnvironment::PrintTo(StringStream* stream) {
9326 for (int i = 0; i < length(); i++) { 9326 for (int i = 0; i < length(); i++) {
9327 if (i == 0) stream->Add("parameters\n"); 9327 if (i == 0) stream->Add("parameters\n");
9328 if (i == parameter_count()) stream->Add("specials\n"); 9328 if (i == parameter_count()) stream->Add("specials\n");
9329 if (i == parameter_count() + specials_count()) stream->Add("locals\n"); 9329 if (i == parameter_count() + specials_count()) stream->Add("locals\n");
9330 if (i == parameter_count() + specials_count() + local_count()) { 9330 if (i == parameter_count() + specials_count() + local_count()) {
(...skipping 333 matching lines...) Expand 10 before | Expand all | Expand 10 after
9664 } 9664 }
9665 } 9665 }
9666 9666
9667 #ifdef DEBUG 9667 #ifdef DEBUG
9668 if (graph_ != NULL) graph_->Verify(false); // No full verify. 9668 if (graph_ != NULL) graph_->Verify(false); // No full verify.
9669 if (allocator_ != NULL) allocator_->Verify(); 9669 if (allocator_ != NULL) allocator_->Verify();
9670 #endif 9670 #endif
9671 } 9671 }
9672 9672
9673 } } // namespace v8::internal 9673 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/hydrogen.h ('k') | src/hydrogen-instructions.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698