Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 106 if (first_ == NULL) { | 106 if (first_ == NULL) { |
| 107 HBlockEntry* entry = new HBlockEntry(); | 107 HBlockEntry* entry = new HBlockEntry(); |
| 108 entry->InitializeAsFirst(this); | 108 entry->InitializeAsFirst(this); |
| 109 first_ = last_ = entry; | 109 first_ = last_ = entry; |
| 110 } | 110 } |
| 111 instr->InsertAfter(last_); | 111 instr->InsertAfter(last_); |
| 112 last_ = instr; | 112 last_ = instr; |
| 113 } | 113 } |
| 114 | 114 |
| 115 | 115 |
| 116 HDeoptimize* HBasicBlock::CreateDeoptimize() { | |
| 117 ASSERT(HasEnvironment()); | |
| 118 HEnvironment* environment = last_environment(); | |
| 119 | |
| 120 HDeoptimize* instr = new HDeoptimize(environment->length()); | |
| 121 | |
| 122 for (int i = 0; i < environment->length(); i++) { | |
| 123 HValue* val = environment->values()->at(i); | |
| 124 instr->AddEnvironmentValue(val); | |
| 125 } | |
| 126 | |
| 127 return instr; | |
| 128 } | |
| 129 | |
| 130 | |
| 116 HSimulate* HBasicBlock::CreateSimulate(int id) { | 131 HSimulate* HBasicBlock::CreateSimulate(int id) { |
| 117 ASSERT(HasEnvironment()); | 132 ASSERT(HasEnvironment()); |
| 118 HEnvironment* environment = last_environment(); | 133 HEnvironment* environment = last_environment(); |
| 119 ASSERT(id == AstNode::kNoNumber || | 134 ASSERT(id == AstNode::kNoNumber || |
| 120 environment->closure()->shared()->VerifyBailoutId(id)); | 135 environment->closure()->shared()->VerifyBailoutId(id)); |
| 121 | 136 |
| 122 int push_count = environment->push_count(); | 137 int push_count = environment->push_count(); |
| 123 int pop_count = environment->pop_count(); | 138 int pop_count = environment->pop_count(); |
| 124 | 139 |
| 125 int length = environment->length(); | 140 int length = environment->length(); |
| (...skipping 2362 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2488 clause->RecordTypeFeedback(oracle()); | 2503 clause->RecordTypeFeedback(oracle()); |
| 2489 if (!clause->IsSmiCompare()) { | 2504 if (!clause->IsSmiCompare()) { |
| 2490 if (current_block() == first_test_block) { | 2505 if (current_block() == first_test_block) { |
| 2491 // If the first test is the one that deopts and if the tag value is | 2506 // If the first test is the one that deopts and if the tag value is |
| 2492 // a phi, we need to have some use of that phi to prevent phi | 2507 // a phi, we need to have some use of that phi to prevent phi |
| 2493 // elimination from removing it. This HSimulate is such a use. | 2508 // elimination from removing it. This HSimulate is such a use. |
| 2494 Push(tag_value); | 2509 Push(tag_value); |
| 2495 AddSimulate(stmt->EntryId()); | 2510 AddSimulate(stmt->EntryId()); |
| 2496 Drop(1); | 2511 Drop(1); |
| 2497 } | 2512 } |
| 2498 current_block()->Finish(new HDeoptimize()); | 2513 |
| 2514 current_block()->FinishWithDeoptimization(); | |
|
Kevin Millikin (Chromium)
2011/03/17 05:31:02
We had code to try to handle this issue with a hac
| |
| 2499 set_current_block(NULL); | 2515 set_current_block(NULL); |
| 2500 break; | 2516 break; |
| 2501 } | 2517 } |
| 2502 | 2518 |
| 2503 // Otherwise generate a compare and branch. | 2519 // Otherwise generate a compare and branch. |
| 2504 VISIT_FOR_VALUE(clause->label()); | 2520 VISIT_FOR_VALUE(clause->label()); |
| 2505 HValue* label_value = Pop(); | 2521 HValue* label_value = Pop(); |
| 2506 HCompare* compare = new HCompare(tag_value, label_value, Token::EQ_STRICT); | 2522 HCompare* compare = new HCompare(tag_value, label_value, Token::EQ_STRICT); |
| 2507 compare->SetInputRepresentation(Representation::Integer32()); | 2523 compare->SetInputRepresentation(Representation::Integer32()); |
| 2508 ASSERT(!compare->HasSideEffects()); | 2524 ASSERT(!compare->HasSideEffects()); |
| (...skipping 599 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3108 current_block()->Goto(join); | 3124 current_block()->Goto(join); |
| 3109 | 3125 |
| 3110 set_current_block(if_false); | 3126 set_current_block(if_false); |
| 3111 } | 3127 } |
| 3112 } | 3128 } |
| 3113 | 3129 |
| 3114 // Finish up. Unconditionally deoptimize if we've handled all the maps we | 3130 // Finish up. Unconditionally deoptimize if we've handled all the maps we |
| 3115 // know about and do not want to handle ones we've never seen. Otherwise | 3131 // know about and do not want to handle ones we've never seen. Otherwise |
| 3116 // use a generic IC. | 3132 // use a generic IC. |
| 3117 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { | 3133 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { |
| 3118 current_block()->FinishExit(new HDeoptimize); | 3134 current_block()->FinishExitWithDeoptimization(); |
| 3119 } else { | 3135 } else { |
| 3120 HInstruction* instr = BuildStoreNamedGeneric(object, name, value); | 3136 HInstruction* instr = BuildStoreNamedGeneric(object, name, value); |
| 3121 instr->set_position(expr->position()); | 3137 instr->set_position(expr->position()); |
| 3122 AddInstruction(instr); | 3138 AddInstruction(instr); |
| 3123 | 3139 |
| 3124 if (join != NULL) { | 3140 if (join != NULL) { |
| 3125 if (!ast_context()->IsEffect()) Push(value); | 3141 if (!ast_context()->IsEffect()) Push(value); |
| 3126 current_block()->Goto(join); | 3142 current_block()->Goto(join); |
| 3127 } else { | 3143 } else { |
| 3128 // The HSimulate for the store should not see the stored value in | 3144 // The HSimulate for the store should not see the stored value in |
| (...skipping 327 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3456 current_block()->Goto(join); | 3472 current_block()->Goto(join); |
| 3457 | 3473 |
| 3458 set_current_block(if_false); | 3474 set_current_block(if_false); |
| 3459 } | 3475 } |
| 3460 } | 3476 } |
| 3461 | 3477 |
| 3462 // Finish up. Unconditionally deoptimize if we've handled all the maps we | 3478 // Finish up. Unconditionally deoptimize if we've handled all the maps we |
| 3463 // know about and do not want to handle ones we've never seen. Otherwise | 3479 // know about and do not want to handle ones we've never seen. Otherwise |
| 3464 // use a generic IC. | 3480 // use a generic IC. |
| 3465 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { | 3481 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { |
| 3466 current_block()->FinishExit(new HDeoptimize); | 3482 current_block()->FinishExitWithDeoptimization(); |
| 3467 } else { | 3483 } else { |
| 3468 HInstruction* instr = BuildLoadNamedGeneric(object, expr); | 3484 HInstruction* instr = BuildLoadNamedGeneric(object, expr); |
| 3469 instr->set_position(expr->position()); | 3485 instr->set_position(expr->position()); |
| 3470 | 3486 |
| 3471 if (join != NULL) { | 3487 if (join != NULL) { |
| 3472 AddInstruction(instr); | 3488 AddInstruction(instr); |
| 3473 if (!ast_context()->IsEffect()) Push(instr); | 3489 if (!ast_context()->IsEffect()) Push(instr); |
| 3474 current_block()->Goto(join); | 3490 current_block()->Goto(join); |
| 3475 } else { | 3491 } else { |
| 3476 ast_context()->ReturnInstruction(instr, expr->id()); | 3492 ast_context()->ReturnInstruction(instr, expr->id()); |
| (...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3821 | 3837 |
| 3822 if (current_block() != NULL) current_block()->Goto(join); | 3838 if (current_block() != NULL) current_block()->Goto(join); |
| 3823 set_current_block(if_false); | 3839 set_current_block(if_false); |
| 3824 } | 3840 } |
| 3825 } | 3841 } |
| 3826 | 3842 |
| 3827 // Finish up. Unconditionally deoptimize if we've handled all the maps we | 3843 // Finish up. Unconditionally deoptimize if we've handled all the maps we |
| 3828 // know about and do not want to handle ones we've never seen. Otherwise | 3844 // know about and do not want to handle ones we've never seen. Otherwise |
| 3829 // use a generic IC. | 3845 // use a generic IC. |
| 3830 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { | 3846 if (count == types->length() && FLAG_deoptimize_uncommon_cases) { |
| 3831 current_block()->FinishExit(new HDeoptimize); | 3847 current_block()->FinishExitWithDeoptimization(); |
| 3832 } else { | 3848 } else { |
| 3833 HContext* context = new HContext; | 3849 HContext* context = new HContext; |
| 3834 AddInstruction(context); | 3850 AddInstruction(context); |
| 3835 HCallNamed* call = new HCallNamed(context, name, argument_count); | 3851 HCallNamed* call = new HCallNamed(context, name, argument_count); |
| 3836 call->set_position(expr->position()); | 3852 call->set_position(expr->position()); |
| 3837 PreProcessCall(call); | 3853 PreProcessCall(call); |
| 3838 | 3854 |
| 3839 if (join != NULL) { | 3855 if (join != NULL) { |
| 3840 AddInstruction(call); | 3856 AddInstruction(call); |
| 3841 if (!ast_context()->IsEffect()) Push(call); | 3857 if (!ast_context()->IsEffect()) Push(call); |
| (...skipping 2083 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 5925 } | 5941 } |
| 5926 } | 5942 } |
| 5927 | 5943 |
| 5928 #ifdef DEBUG | 5944 #ifdef DEBUG |
| 5929 if (graph_ != NULL) graph_->Verify(); | 5945 if (graph_ != NULL) graph_->Verify(); |
| 5930 if (allocator_ != NULL) allocator_->Verify(); | 5946 if (allocator_ != NULL) allocator_->Verify(); |
| 5931 #endif | 5947 #endif |
| 5932 } | 5948 } |
| 5933 | 5949 |
| 5934 } } // namespace v8::internal | 5950 } } // namespace v8::internal |
| OLD | NEW |