Mark map-transition stores as map-changing instructions.
This prevents code motion from hoisting map-checks across such stores which may result in unnecessary deoptimizations. In the following example program we would move a map-check from the inner loop out before the outer loop which is not desirable: function f() { var o = {}; var j = 0; o.a = 1; do { o.b = 6; // Map transition for (var i=0; i<10; i++) { o.a = o.b + i; } } while(++j < 1) {} } for (var i = 0; i < 1000000; i++) f(); Review URL: http://codereview.chromium.org/5991001 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@6071 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
06ac3b18a0
commit
6cc0310a72
@ -579,6 +579,13 @@ void HBranch::PrintDataTo(StringStream* stream) const {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void HCompareMapAndBranch::PrintDataTo(StringStream* stream) const {
|
||||||
|
stream->Add("on ");
|
||||||
|
value()->PrintNameTo(stream);
|
||||||
|
stream->Add(" (%p)", *map());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void HGoto::PrintDataTo(StringStream* stream) const {
|
void HGoto::PrintDataTo(StringStream* stream) const {
|
||||||
stream->Add("B%d", FirstSuccessor()->block_id());
|
stream->Add("B%d", FirstSuccessor()->block_id());
|
||||||
}
|
}
|
||||||
|
@ -905,6 +905,8 @@ class HCompareMapAndBranch: public HUnaryControlInstruction {
|
|||||||
virtual HBasicBlock* FirstSuccessor() const { return true_destination_; }
|
virtual HBasicBlock* FirstSuccessor() const { return true_destination_; }
|
||||||
virtual HBasicBlock* SecondSuccessor() const { return false_destination_; }
|
virtual HBasicBlock* SecondSuccessor() const { return false_destination_; }
|
||||||
|
|
||||||
|
virtual void PrintDataTo(StringStream* stream) const;
|
||||||
|
|
||||||
Handle<Map> map() const { return map_; }
|
Handle<Map> map() const { return map_; }
|
||||||
|
|
||||||
DECLARE_CONCRETE_INSTRUCTION(CompareMapAndBranch, "compare_map_and_branch")
|
DECLARE_CONCRETE_INSTRUCTION(CompareMapAndBranch, "compare_map_and_branch")
|
||||||
|
@ -3165,6 +3165,9 @@ HInstruction* HGraphBuilder::BuildStoreNamedField(HValue* object,
|
|||||||
if (lookup->type() == MAP_TRANSITION) {
|
if (lookup->type() == MAP_TRANSITION) {
|
||||||
Handle<Map> transition(lookup->GetTransitionMapFromMap(*type));
|
Handle<Map> transition(lookup->GetTransitionMapFromMap(*type));
|
||||||
instr->set_transition(transition);
|
instr->set_transition(transition);
|
||||||
|
// TODO(fschneider): Record the new map type of the object in the IR to
|
||||||
|
// enable elimination of redundant checks after the transition store.
|
||||||
|
instr->SetFlag(HValue::kChangesMaps);
|
||||||
}
|
}
|
||||||
return instr;
|
return instr;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user