Chromium Code Reviews

Side by Side Diff: src/hydrogen.cc

Issue 10534006: Remove TLS access for current Zone. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 8 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
View unified diff | | Annotate | Revision Log
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 37 matching lines...)
48 #else 48 #else
49 #error Unsupported target architecture. 49 #error Unsupported target architecture.
50 #endif 50 #endif
51 51
52 namespace v8 { 52 namespace v8 {
53 namespace internal { 53 namespace internal {
54 54
55 HBasicBlock::HBasicBlock(HGraph* graph) 55 HBasicBlock::HBasicBlock(HGraph* graph)
56 : block_id_(graph->GetNextBlockID()), 56 : block_id_(graph->GetNextBlockID()),
57 graph_(graph), 57 graph_(graph),
58 phis_(4), 58 phis_(4, graph->zone()),
59 first_(NULL), 59 first_(NULL),
60 last_(NULL), 60 last_(NULL),
61 end_(NULL), 61 end_(NULL),
62 loop_information_(NULL), 62 loop_information_(NULL),
63 predecessors_(2), 63 predecessors_(2, graph->zone()),
64 dominator_(NULL), 64 dominator_(NULL),
65 dominated_blocks_(4), 65 dominated_blocks_(4, graph->zone()),
66 last_environment_(NULL), 66 last_environment_(NULL),
67 argument_count_(-1), 67 argument_count_(-1),
68 first_instruction_index_(-1), 68 first_instruction_index_(-1),
69 last_instruction_index_(-1), 69 last_instruction_index_(-1),
70 deleted_phis_(4), 70 deleted_phis_(4, graph->zone()),
71 parent_loop_header_(NULL), 71 parent_loop_header_(NULL),
72 is_inline_return_target_(false), 72 is_inline_return_target_(false),
73 is_deoptimizing_(false), 73 is_deoptimizing_(false),
74 dominates_loop_successors_(false) { } 74 dominates_loop_successors_(false) { }
75 75
76 76
77 void HBasicBlock::AttachLoopInformation() { 77 void HBasicBlock::AttachLoopInformation() {
78 ASSERT(!IsLoopHeader()); 78 ASSERT(!IsLoopHeader());
79 loop_information_ = new(zone()) HLoopInformation(this); 79 loop_information_ = new(zone()) HLoopInformation(this, zone());
80 } 80 }
81 81
82 82
83 void HBasicBlock::DetachLoopInformation() { 83 void HBasicBlock::DetachLoopInformation() {
84 ASSERT(IsLoopHeader()); 84 ASSERT(IsLoopHeader());
85 loop_information_ = NULL; 85 loop_information_ = NULL;
86 } 86 }
87 87
88 88
89 void HBasicBlock::AddPhi(HPhi* phi) { 89 void HBasicBlock::AddPhi(HPhi* phi) {
90 ASSERT(!IsStartBlock()); 90 ASSERT(!IsStartBlock());
91 phis_.Add(phi); 91 phis_.Add(phi, zone());
92 phi->SetBlock(this); 92 phi->SetBlock(this);
93 } 93 }
94 94
95 95
96 void HBasicBlock::RemovePhi(HPhi* phi) { 96 void HBasicBlock::RemovePhi(HPhi* phi) {
97 ASSERT(phi->block() == this); 97 ASSERT(phi->block() == this);
98 ASSERT(phis_.Contains(phi)); 98 ASSERT(phis_.Contains(phi));
99 ASSERT(phi->HasNoUses() || !phi->is_live()); 99 ASSERT(phi->HasNoUses() || !phi->is_live());
100 phi->Kill(); 100 phi->Kill();
101 phis_.RemoveElement(phi); 101 phis_.RemoveElement(phi);
(...skipping 10 matching lines...)
112 entry->InitializeAsFirst(this); 112 entry->InitializeAsFirst(this);
113 first_ = last_ = entry; 113 first_ = last_ = entry;
114 } 114 }
115 instr->InsertAfter(last_); 115 instr->InsertAfter(last_);
116 } 116 }
117 117
118 118
119 HDeoptimize* HBasicBlock::CreateDeoptimize( 119 HDeoptimize* HBasicBlock::CreateDeoptimize(
120 HDeoptimize::UseEnvironment has_uses) { 120 HDeoptimize::UseEnvironment has_uses) {
121 ASSERT(HasEnvironment()); 121 ASSERT(HasEnvironment());
122 if (has_uses == HDeoptimize::kNoUses) return new(zone()) HDeoptimize(0); 122 if (has_uses == HDeoptimize::kNoUses)
123 return new(zone()) HDeoptimize(0, zone());
123 124
124 HEnvironment* environment = last_environment(); 125 HEnvironment* environment = last_environment();
125 HDeoptimize* instr = new(zone()) HDeoptimize(environment->length()); 126 HDeoptimize* instr = new(zone()) HDeoptimize(environment->length(), zone());
126 for (int i = 0; i < environment->length(); i++) { 127 for (int i = 0; i < environment->length(); i++) {
127 HValue* val = environment->values()->at(i); 128 HValue* val = environment->values()->at(i);
128 instr->AddEnvironmentValue(val); 129 instr->AddEnvironmentValue(val, zone());
129 } 130 }
130 131
131 return instr; 132 return instr;
132 } 133 }
133 134
134 135
135 HSimulate* HBasicBlock::CreateSimulate(int ast_id) { 136 HSimulate* HBasicBlock::CreateSimulate(int ast_id) {
136 ASSERT(HasEnvironment()); 137 ASSERT(HasEnvironment());
137 HEnvironment* environment = last_environment(); 138 HEnvironment* environment = last_environment();
138 ASSERT(ast_id == AstNode::kNoNumber || 139 ASSERT(ast_id == AstNode::kNoNumber ||
139 environment->closure()->shared()->VerifyBailoutId(ast_id)); 140 environment->closure()->shared()->VerifyBailoutId(ast_id));
140 141
141 int push_count = environment->push_count(); 142 int push_count = environment->push_count();
142 int pop_count = environment->pop_count(); 143 int pop_count = environment->pop_count();
143 144
144 HSimulate* instr = new(zone()) HSimulate(ast_id, pop_count); 145 HSimulate* instr = new(zone()) HSimulate(ast_id, pop_count, zone());
145 for (int i = push_count - 1; i >= 0; --i) { 146 for (int i = push_count - 1; i >= 0; --i) {
146 instr->AddPushedValue(environment->ExpressionStackAt(i)); 147 instr->AddPushedValue(environment->ExpressionStackAt(i));
147 } 148 }
148 for (int i = 0; i < environment->assigned_variables()->length(); ++i) { 149 for (int i = 0; i < environment->assigned_variables()->length(); ++i) {
149 int index = environment->assigned_variables()->at(i); 150 int index = environment->assigned_variables()->at(i);
150 instr->AddAssignedValue(index, environment->Lookup(index)); 151 instr->AddAssignedValue(index, environment->Lookup(index));
151 } 152 }
152 environment->ClearHistory(); 153 environment->ClearHistory();
153 return instr; 154 return instr;
154 } 155 }
(...skipping 116 matching lines...)
271 phis_[i]->AddInput(incoming_env->values()->at(i)); 272 phis_[i]->AddInput(incoming_env->values()->at(i));
272 } 273 }
273 } else { 274 } else {
274 last_environment()->AddIncomingEdge(this, pred->last_environment()); 275 last_environment()->AddIncomingEdge(this, pred->last_environment());
275 } 276 }
276 } else if (!HasEnvironment() && !IsFinished()) { 277 } else if (!HasEnvironment() && !IsFinished()) {
277 ASSERT(!IsLoopHeader()); 278 ASSERT(!IsLoopHeader());
278 SetInitialEnvironment(pred->last_environment()->Copy()); 279 SetInitialEnvironment(pred->last_environment()->Copy());
279 } 280 }
280 281
281 predecessors_.Add(pred); 282 predecessors_.Add(pred, zone());
282 } 283 }
283 284
284 285
285 void HBasicBlock::AddDominatedBlock(HBasicBlock* block) { 286 void HBasicBlock::AddDominatedBlock(HBasicBlock* block) {
286 ASSERT(!dominated_blocks_.Contains(block)); 287 ASSERT(!dominated_blocks_.Contains(block));
287 // Keep the list of dominated blocks sorted such that if there is two 288 // Keep the list of dominated blocks sorted such that if there is two
288 // succeeding block in this list, the predecessor is before the successor. 289 // succeeding block in this list, the predecessor is before the successor.
289 int index = 0; 290 int index = 0;
290 while (index < dominated_blocks_.length() && 291 while (index < dominated_blocks_.length() &&
291 dominated_blocks_[index]->block_id() < block->block_id()) { 292 dominated_blocks_[index]->block_id() < block->block_id()) {
292 ++index; 293 ++index;
293 } 294 }
294 dominated_blocks_.InsertAt(index, block); 295 dominated_blocks_.InsertAt(index, block, zone());
295 } 296 }
296 297
297 298
298 void HBasicBlock::AssignCommonDominator(HBasicBlock* other) { 299 void HBasicBlock::AssignCommonDominator(HBasicBlock* other) {
299 if (dominator_ == NULL) { 300 if (dominator_ == NULL) {
300 dominator_ = other; 301 dominator_ = other;
301 other->AddDominatedBlock(this); 302 other->AddDominatedBlock(this);
302 } else if (other->dominator() != NULL) { 303 } else if (other->dominator() != NULL) {
303 HBasicBlock* first = dominator_; 304 HBasicBlock* first = dominator_;
304 HBasicBlock* second = other; 305 HBasicBlock* second = other;
(...skipping 92 matching lines...)
397 if (predecessors_.length() > 1) { 398 if (predecessors_.length() > 1) {
398 for (int i = 0; i < predecessors_.length(); ++i) { 399 for (int i = 0; i < predecessors_.length(); ++i) {
399 ASSERT(predecessors_[i]->end()->SecondSuccessor() == NULL); 400 ASSERT(predecessors_[i]->end()->SecondSuccessor() == NULL);
400 } 401 }
401 } 402 }
402 } 403 }
403 #endif 404 #endif
404 405
405 406
406 void HLoopInformation::RegisterBackEdge(HBasicBlock* block) { 407 void HLoopInformation::RegisterBackEdge(HBasicBlock* block) {
407 this->back_edges_.Add(block); 408 this->back_edges_.Add(block, block->zone());
408 AddBlock(block); 409 AddBlock(block);
409 } 410 }
410 411
411 412
412 HBasicBlock* HLoopInformation::GetLastBackEdge() const { 413 HBasicBlock* HLoopInformation::GetLastBackEdge() const {
413 int max_id = -1; 414 int max_id = -1;
414 HBasicBlock* result = NULL; 415 HBasicBlock* result = NULL;
415 for (int i = 0; i < back_edges_.length(); ++i) { 416 for (int i = 0; i < back_edges_.length(); ++i) {
416 HBasicBlock* cur = back_edges_[i]; 417 HBasicBlock* cur = back_edges_[i];
417 if (cur->block_id() > max_id) { 418 if (cur->block_id() > max_id) {
418 max_id = cur->block_id(); 419 max_id = cur->block_id();
419 result = cur; 420 result = cur;
420 } 421 }
421 } 422 }
422 return result; 423 return result;
423 } 424 }
424 425
425 426
426 void HLoopInformation::AddBlock(HBasicBlock* block) { 427 void HLoopInformation::AddBlock(HBasicBlock* block) {
427 if (block == loop_header()) return; 428 if (block == loop_header()) return;
428 if (block->parent_loop_header() == loop_header()) return; 429 if (block->parent_loop_header() == loop_header()) return;
429 if (block->parent_loop_header() != NULL) { 430 if (block->parent_loop_header() != NULL) {
430 AddBlock(block->parent_loop_header()); 431 AddBlock(block->parent_loop_header());
431 } else { 432 } else {
432 block->set_parent_loop_header(loop_header()); 433 block->set_parent_loop_header(loop_header());
433 blocks_.Add(block); 434 blocks_.Add(block, block->zone());
434 for (int i = 0; i < block->predecessors()->length(); ++i) { 435 for (int i = 0; i < block->predecessors()->length(); ++i) {
435 AddBlock(block->predecessors()->at(i)); 436 AddBlock(block->predecessors()->at(i));
436 } 437 }
437 } 438 }
438 } 439 }
439 440
440 441
441 #ifdef DEBUG 442 #ifdef DEBUG
442 443
443 // Checks reachability of the blocks in this graph and stores a bit in 444 // Checks reachability of the blocks in this graph and stores a bit in
444 // the BitVector "reachable()" for every block that can be reached 445 // the BitVector "reachable()" for every block that can be reached
445 // from the start block of the graph. If "dont_visit" is non-null, the given 446 // from the start block of the graph. If "dont_visit" is non-null, the given
446 // block is treated as if it would not be part of the graph. "visited_count()" 447 // block is treated as if it would not be part of the graph. "visited_count()"
447 // returns the number of reachable blocks. 448 // returns the number of reachable blocks.
448 class ReachabilityAnalyzer BASE_EMBEDDED { 449 class ReachabilityAnalyzer BASE_EMBEDDED {
449 public: 450 public:
450 ReachabilityAnalyzer(HBasicBlock* entry_block, 451 ReachabilityAnalyzer(HBasicBlock* entry_block,
451 int block_count, 452 int block_count,
452 HBasicBlock* dont_visit) 453 HBasicBlock* dont_visit)
453 : visited_count_(0), 454 : visited_count_(0),
454 stack_(16), 455 stack_(16, entry_block->zone()),
455 reachable_(block_count, ZONE), 456 reachable_(block_count, entry_block->zone()),
456 dont_visit_(dont_visit) { 457 dont_visit_(dont_visit) {
457 PushBlock(entry_block); 458 PushBlock(entry_block);
458 Analyze(); 459 Analyze();
459 } 460 }
460 461
461 int visited_count() const { return visited_count_; } 462 int visited_count() const { return visited_count_; }
462 const BitVector* reachable() const { return &reachable_; } 463 const BitVector* reachable() const { return &reachable_; }
463 464
464 private: 465 private:
465 void PushBlock(HBasicBlock* block) { 466 void PushBlock(HBasicBlock* block) {
466 if (block != NULL && block != dont_visit_ && 467 if (block != NULL && block != dont_visit_ &&
467 !reachable_.Contains(block->block_id())) { 468 !reachable_.Contains(block->block_id())) {
468 reachable_.Add(block->block_id()); 469 reachable_.Add(block->block_id());
469 stack_.Add(block); 470 stack_.Add(block, block->zone());
470 visited_count_++; 471 visited_count_++;
471 } 472 }
472 } 473 }
473 474
474 void Analyze() { 475 void Analyze() {
475 while (!stack_.is_empty()) { 476 while (!stack_.is_empty()) {
476 HControlInstruction* end = stack_.RemoveLast()->end(); 477 HControlInstruction* end = stack_.RemoveLast()->end();
477 for (HSuccessorIterator it(end); !it.Done(); it.Advance()) { 478 for (HSuccessorIterator it(end); !it.Done(); it.Advance()) {
478 PushBlock(it.Current()); 479 PushBlock(it.Current());
479 } 480 }
(...skipping 117 matching lines...)
597 return GetConstant(&constant_false_, isolate()->heap()->false_value()); 598 return GetConstant(&constant_false_, isolate()->heap()->false_value());
598 } 599 }
599 600
600 601
601 HConstant* HGraph::GetConstantHole() { 602 HConstant* HGraph::GetConstantHole() {
602 return GetConstant(&constant_hole_, isolate()->heap()->the_hole_value()); 603 return GetConstant(&constant_hole_, isolate()->heap()->the_hole_value());
603 } 604 }
604 605
605 606
606 HGraphBuilder::HGraphBuilder(CompilationInfo* info, 607 HGraphBuilder::HGraphBuilder(CompilationInfo* info,
607 TypeFeedbackOracle* oracle) 608 TypeFeedbackOracle* oracle,
609 Zone* zone)
608 : function_state_(NULL), 610 : function_state_(NULL),
609 initial_function_state_(this, info, oracle, NORMAL_RETURN), 611 initial_function_state_(this, info, oracle, NORMAL_RETURN),
610 ast_context_(NULL), 612 ast_context_(NULL),
611 break_scope_(NULL), 613 break_scope_(NULL),
612 graph_(NULL), 614 graph_(NULL),
613 current_block_(NULL), 615 current_block_(NULL),
614 inlined_count_(0), 616 inlined_count_(0),
615 globals_(10), 617 globals_(10, zone),
616 zone_(info->isolate()->zone()), 618 zone_(zone),
617 inline_bailout_(false) { 619 inline_bailout_(false) {
618 // This is not initialized in the initializer list because the 620 // This is not initialized in the initializer list because the
619 // constructor for the initial state relies on function_state_ == NULL 621 // constructor for the initial state relies on function_state_ == NULL
620 // to know it's the initial state. 622 // to know it's the initial state.
621 function_state_= &initial_function_state_; 623 function_state_= &initial_function_state_;
622 } 624 }
623 625
624 HBasicBlock* HGraphBuilder::CreateJoin(HBasicBlock* first, 626 HBasicBlock* HGraphBuilder::CreateJoin(HBasicBlock* first,
625 HBasicBlock* second, 627 HBasicBlock* second,
626 int join_id) { 628 int join_id) {
(...skipping 38 matching lines...)
665 return loop_successor; 667 return loop_successor;
666 } 668 }
667 669
668 670
669 void HBasicBlock::FinishExit(HControlInstruction* instruction) { 671 void HBasicBlock::FinishExit(HControlInstruction* instruction) {
670 Finish(instruction); 672 Finish(instruction);
671 ClearEnvironment(); 673 ClearEnvironment();
672 } 674 }
673 675
674 676
675 HGraph::HGraph(CompilationInfo* info) 677 HGraph::HGraph(CompilationInfo* info, Zone* zone)
676 : isolate_(info->isolate()), 678 : isolate_(info->isolate()),
677 next_block_id_(0), 679 next_block_id_(0),
678 entry_block_(NULL), 680 entry_block_(NULL),
679 blocks_(8), 681 blocks_(8, zone),
680 values_(16), 682 values_(16, zone),
681 phi_list_(NULL) { 683 phi_list_(NULL),
684 zone_(zone) {
682 start_environment_ = 685 start_environment_ =
683 new(zone()) HEnvironment(NULL, info->scope(), info->closure()); 686 new(zone) HEnvironment(NULL, info->scope(), info->closure(), zone);
684 start_environment_->set_ast_id(AstNode::kFunctionEntryId); 687 start_environment_->set_ast_id(AstNode::kFunctionEntryId);
685 entry_block_ = CreateBasicBlock(); 688 entry_block_ = CreateBasicBlock();
686 entry_block_->SetInitialEnvironment(start_environment_); 689 entry_block_->SetInitialEnvironment(start_environment_);
687 } 690 }
688 691
689 692
690 Handle<Code> HGraph::Compile(CompilationInfo* info, Zone* zone) { 693 Handle<Code> HGraph::Compile(CompilationInfo* info, Zone* zone) {
691 int values = GetMaximumValueID(); 694 int values = GetMaximumValueID();
692 if (values > LUnallocated::kMaxVirtualRegisters) { 695 if (values > LUnallocated::kMaxVirtualRegisters) {
693 if (FLAG_trace_bailout) { 696 if (FLAG_trace_bailout) {
(...skipping 29 matching lines...)
723 generator.FinishCode(code); 726 generator.FinishCode(code);
724 CodeGenerator::PrintCode(code, info); 727 CodeGenerator::PrintCode(code, info);
725 return code; 728 return code;
726 } 729 }
727 return Handle<Code>::null(); 730 return Handle<Code>::null();
728 } 731 }
729 732
730 733
731 HBasicBlock* HGraph::CreateBasicBlock() { 734 HBasicBlock* HGraph::CreateBasicBlock() {
732 HBasicBlock* result = new(zone()) HBasicBlock(this); 735 HBasicBlock* result = new(zone()) HBasicBlock(this);
733 blocks_.Add(result); 736 blocks_.Add(result, zone());
734 return result; 737 return result;
735 } 738 }
736 739
737 740
738 void HGraph::Canonicalize() { 741 void HGraph::Canonicalize() {
739 if (!FLAG_use_canonicalizing) return; 742 if (!FLAG_use_canonicalizing) return;
740 HPhase phase("H_Canonicalize", this); 743 HPhase phase("H_Canonicalize", this);
741 for (int i = 0; i < blocks()->length(); ++i) { 744 for (int i = 0; i < blocks()->length(); ++i) {
742 HInstruction* instr = blocks()->at(i)->first(); 745 HInstruction* instr = blocks()->at(i)->first();
743 while (instr != NULL) { 746 while (instr != NULL) {
744 HValue* value = instr->Canonicalize(); 747 HValue* value = instr->Canonicalize();
745 if (value != instr) instr->DeleteAndReplaceWith(value); 748 if (value != instr) instr->DeleteAndReplaceWith(value);
746 instr = instr->next(); 749 instr = instr->next();
747 } 750 }
748 } 751 }
749 } 752 }
750 753
751 754
752 void HGraph::OrderBlocks() { 755 void HGraph::OrderBlocks() {
753 HPhase phase("H_Block ordering"); 756 HPhase phase("H_Block ordering");
754 BitVector visited(blocks_.length(), zone()); 757 BitVector visited(blocks_.length(), zone());
755 758
756 ZoneList<HBasicBlock*> reverse_result(8); 759 ZoneList<HBasicBlock*> reverse_result(8, zone());
757 HBasicBlock* start = blocks_[0]; 760 HBasicBlock* start = blocks_[0];
758 Postorder(start, &visited, &reverse_result, NULL); 761 Postorder(start, &visited, &reverse_result, NULL);
759 762
760 blocks_.Rewind(0); 763 blocks_.Rewind(0);
761 int index = 0; 764 int index = 0;
762 for (int i = reverse_result.length() - 1; i >= 0; --i) { 765 for (int i = reverse_result.length() - 1; i >= 0; --i) {
763 HBasicBlock* b = reverse_result[i]; 766 HBasicBlock* b = reverse_result[i];
764 blocks_.Add(b); 767 blocks_.Add(b, zone());
765 b->set_block_id(index++); 768 b->set_block_id(index++);
766 } 769 }
767 } 770 }
768 771
769 772
770 void HGraph::PostorderLoopBlocks(HLoopInformation* loop, 773 void HGraph::PostorderLoopBlocks(HLoopInformation* loop,
771 BitVector* visited, 774 BitVector* visited,
772 ZoneList<HBasicBlock*>* order, 775 ZoneList<HBasicBlock*>* order,
773 HBasicBlock* loop_header) { 776 HBasicBlock* loop_header) {
774 for (int i = 0; i < loop->blocks()->length(); ++i) { 777 for (int i = 0; i < loop->blocks()->length(); ++i) {
(...skipping 25 matching lines...)
800 for (HSuccessorIterator it(block->end()); !it.Done(); it.Advance()) { 803 for (HSuccessorIterator it(block->end()); !it.Done(); it.Advance()) {
801 Postorder(it.Current(), visited, order, loop_header); 804 Postorder(it.Current(), visited, order, loop_header);
802 } 805 }
803 } 806 }
804 ASSERT(block->end()->FirstSuccessor() == NULL || 807 ASSERT(block->end()->FirstSuccessor() == NULL ||
805 order->Contains(block->end()->FirstSuccessor()) || 808 order->Contains(block->end()->FirstSuccessor()) ||
806 block->end()->FirstSuccessor()->IsLoopHeader()); 809 block->end()->FirstSuccessor()->IsLoopHeader());
807 ASSERT(block->end()->SecondSuccessor() == NULL || 810 ASSERT(block->end()->SecondSuccessor() == NULL ||
808 order->Contains(block->end()->SecondSuccessor()) || 811 order->Contains(block->end()->SecondSuccessor()) ||
809 block->end()->SecondSuccessor()->IsLoopHeader()); 812 block->end()->SecondSuccessor()->IsLoopHeader());
810 order->Add(block); 813 order->Add(block, zone());
811 } 814 }
812 815
813 816
814 void HGraph::AssignDominators() { 817 void HGraph::AssignDominators() {
815 HPhase phase("H_Assign dominators", this); 818 HPhase phase("H_Assign dominators", this);
816 for (int i = 0; i < blocks_.length(); ++i) { 819 for (int i = 0; i < blocks_.length(); ++i) {
817 HBasicBlock* block = blocks_[i]; 820 HBasicBlock* block = blocks_[i];
818 if (block->IsLoopHeader()) { 821 if (block->IsLoopHeader()) {
819 // Only the first predecessor of a loop header is from outside the loop. 822 // Only the first predecessor of a loop header is from outside the loop.
820 // All others are back edges, and thus cannot dominate the loop header. 823 // All others are back edges, and thus cannot dominate the loop header.
(...skipping 21 matching lines...)
842 MarkAsDeoptimizingRecursively(dominated); 845 MarkAsDeoptimizingRecursively(dominated);
843 } 846 }
844 } 847 }
845 848
846 void HGraph::EliminateRedundantPhis() { 849 void HGraph::EliminateRedundantPhis() {
847 HPhase phase("H_Redundant phi elimination", this); 850 HPhase phase("H_Redundant phi elimination", this);
848 851
849 // Worklist of phis that can potentially be eliminated. Initialized with 852 // Worklist of phis that can potentially be eliminated. Initialized with
850 // all phi nodes. When elimination of a phi node modifies another phi node 853 // all phi nodes. When elimination of a phi node modifies another phi node
851 // the modified phi node is added to the worklist. 854 // the modified phi node is added to the worklist.
852 ZoneList<HPhi*> worklist(blocks_.length()); 855 ZoneList<HPhi*> worklist(blocks_.length(), zone());
853 for (int i = 0; i < blocks_.length(); ++i) { 856 for (int i = 0; i < blocks_.length(); ++i) {
854 worklist.AddAll(*blocks_[i]->phis()); 857 worklist.AddAll(*blocks_[i]->phis(), zone());
855 } 858 }
856 859
857 while (!worklist.is_empty()) { 860 while (!worklist.is_empty()) {
858 HPhi* phi = worklist.RemoveLast(); 861 HPhi* phi = worklist.RemoveLast();
859 HBasicBlock* block = phi->block(); 862 HBasicBlock* block = phi->block();
860 863
861 // Skip phi node if it was already replaced. 864 // Skip phi node if it was already replaced.
862 if (block == NULL) continue; 865 if (block == NULL) continue;
863 866
864 // Get replacement value if phi is redundant. 867 // Get replacement value if phi is redundant.
865 HValue* replacement = phi->GetRedundantReplacement(); 868 HValue* replacement = phi->GetRedundantReplacement();
866 869
867 if (replacement != NULL) { 870 if (replacement != NULL) {
868 // Iterate through the uses and replace them all. 871 // Iterate through the uses and replace them all.
869 for (HUseIterator it(phi->uses()); !it.Done(); it.Advance()) { 872 for (HUseIterator it(phi->uses()); !it.Done(); it.Advance()) {
870 HValue* value = it.value(); 873 HValue* value = it.value();
871 value->SetOperandAt(it.index(), replacement); 874 value->SetOperandAt(it.index(), replacement);
872 if (value->IsPhi()) worklist.Add(HPhi::cast(value)); 875 if (value->IsPhi()) worklist.Add(HPhi::cast(value), zone());
873 } 876 }
874 block->RemovePhi(phi); 877 block->RemovePhi(phi);
875 } 878 }
876 } 879 }
877 } 880 }
878 881
879 882
880 void HGraph::EliminateUnreachablePhis() { 883 void HGraph::EliminateUnreachablePhis() {
881 HPhase phase("H_Unreachable phi elimination", this); 884 HPhase phase("H_Unreachable phi elimination", this);
882 885
883 // Initialize worklist. 886 // Initialize worklist.
884 ZoneList<HPhi*> phi_list(blocks_.length()); 887 ZoneList<HPhi*> phi_list(blocks_.length(), zone());
885 ZoneList<HPhi*> worklist(blocks_.length()); 888 ZoneList<HPhi*> worklist(blocks_.length(), zone());
886 for (int i = 0; i < blocks_.length(); ++i) { 889 for (int i = 0; i < blocks_.length(); ++i) {
887 for (int j = 0; j < blocks_[i]->phis()->length(); j++) { 890 for (int j = 0; j < blocks_[i]->phis()->length(); j++) {
888 HPhi* phi = blocks_[i]->phis()->at(j); 891 HPhi* phi = blocks_[i]->phis()->at(j);
889 phi_list.Add(phi); 892 phi_list.Add(phi, zone());
890 // We can't eliminate phis in the receiver position in the environment 893 // We can't eliminate phis in the receiver position in the environment
891 // because in case of throwing an error we need this value to 894 // because in case of throwing an error we need this value to
892 // construct a stack trace. 895 // construct a stack trace.
893 if (phi->HasRealUses() || phi->IsReceiver()) { 896 if (phi->HasRealUses() || phi->IsReceiver()) {
894 phi->set_is_live(true); 897 phi->set_is_live(true);
895 worklist.Add(phi); 898 worklist.Add(phi, zone());
896 } 899 }
897 } 900 }
898 } 901 }
899 902
900 // Iteratively mark live phis. 903 // Iteratively mark live phis.
901 while (!worklist.is_empty()) { 904 while (!worklist.is_empty()) {
902 HPhi* phi = worklist.RemoveLast(); 905 HPhi* phi = worklist.RemoveLast();
903 for (int i = 0; i < phi->OperandCount(); i++) { 906 for (int i = 0; i < phi->OperandCount(); i++) {
904 HValue* operand = phi->OperandAt(i); 907 HValue* operand = phi->OperandAt(i);
905 if (operand->IsPhi() && !HPhi::cast(operand)->is_live()) { 908 if (operand->IsPhi() && !HPhi::cast(operand)->is_live()) {
906 HPhi::cast(operand)->set_is_live(true); 909 HPhi::cast(operand)->set_is_live(true);
907 worklist.Add(HPhi::cast(operand)); 910 worklist.Add(HPhi::cast(operand), zone());
908 } 911 }
909 } 912 }
910 } 913 }
911 914
912 // Remove unreachable phis. 915 // Remove unreachable phis.
913 for (int i = 0; i < phi_list.length(); i++) { 916 for (int i = 0; i < phi_list.length(); i++) {
914 HPhi* phi = phi_list[i]; 917 HPhi* phi = phi_list[i];
915 if (!phi->is_live()) { 918 if (!phi->is_live()) {
916 HBasicBlock* block = phi->block(); 919 HBasicBlock* block = phi->block();
917 block->RemovePhi(phi); 920 block->RemovePhi(phi);
(...skipping 26 matching lines...)
944 if (phi->OperandAt(k) == GetConstantHole()) return false; 947 if (phi->OperandAt(k) == GetConstantHole()) return false;
945 } 948 }
946 } 949 }
947 } 950 }
948 return true; 951 return true;
949 } 952 }
950 953
951 954
952 void HGraph::CollectPhis() { 955 void HGraph::CollectPhis() {
953 int block_count = blocks_.length(); 956 int block_count = blocks_.length();
954 phi_list_ = new ZoneList<HPhi*>(block_count); 957 phi_list_ = new(zone()) ZoneList<HPhi*>(block_count, zone());
955 for (int i = 0; i < block_count; ++i) { 958 for (int i = 0; i < block_count; ++i) {
956 for (int j = 0; j < blocks_[i]->phis()->length(); ++j) { 959 for (int j = 0; j < blocks_[i]->phis()->length(); ++j) {
957 HPhi* phi = blocks_[i]->phis()->at(j); 960 HPhi* phi = blocks_[i]->phis()->at(j);
958 phi_list_->Add(phi); 961 phi_list_->Add(phi, zone());
959 } 962 }
960 } 963 }
961 } 964 }
962 965
963 966
964 void HGraph::InferTypes(ZoneList<HValue*>* worklist) { 967 void HGraph::InferTypes(ZoneList<HValue*>* worklist) {
965 BitVector in_worklist(GetMaximumValueID(), zone()); 968 BitVector in_worklist(GetMaximumValueID(), zone());
966 for (int i = 0; i < worklist->length(); ++i) { 969 for (int i = 0; i < worklist->length(); ++i) {
967 ASSERT(!in_worklist.Contains(worklist->at(i)->id())); 970 ASSERT(!in_worklist.Contains(worklist->at(i)->id()));
968 in_worklist.Add(worklist->at(i)->id()); 971 in_worklist.Add(worklist->at(i)->id());
969 } 972 }
970 973
971 while (!worklist->is_empty()) { 974 while (!worklist->is_empty()) {
972 HValue* current = worklist->RemoveLast(); 975 HValue* current = worklist->RemoveLast();
973 in_worklist.Remove(current->id()); 976 in_worklist.Remove(current->id());
974 if (current->UpdateInferredType()) { 977 if (current->UpdateInferredType()) {
975 for (HUseIterator it(current->uses()); !it.Done(); it.Advance()) { 978 for (HUseIterator it(current->uses()); !it.Done(); it.Advance()) {
976 HValue* use = it.value(); 979 HValue* use = it.value();
977 if (!in_worklist.Contains(use->id())) { 980 if (!in_worklist.Contains(use->id())) {
978 in_worklist.Add(use->id()); 981 in_worklist.Add(use->id());
979 worklist->Add(use); 982 worklist->Add(use, zone());
980 } 983 }
981 } 984 }
982 } 985 }
983 } 986 }
984 } 987 }
985 988
986 989
987 class HRangeAnalysis BASE_EMBEDDED { 990 class HRangeAnalysis BASE_EMBEDDED {
988 public: 991 public:
989 explicit HRangeAnalysis(HGraph* graph) : 992 explicit HRangeAnalysis(HGraph* graph) :
990 graph_(graph), zone_(graph->isolate()->zone()), changed_ranges_(16) { } 993 graph_(graph), zone_(graph->zone()), changed_ranges_(16, zone_) { }
991 994
992 void Analyze(); 995 void Analyze();
993 996
994 private: 997 private:
995 void TraceRange(const char* msg, ...); 998 void TraceRange(const char* msg, ...);
996 void Analyze(HBasicBlock* block); 999 void Analyze(HBasicBlock* block);
997 void InferControlFlowRange(HCompareIDAndBranch* test, HBasicBlock* dest); 1000 void InferControlFlowRange(HCompareIDAndBranch* test, HBasicBlock* dest);
998 void UpdateControlFlowRange(Token::Value op, HValue* value, HValue* other); 1001 void UpdateControlFlowRange(Token::Value op, HValue* value, HValue* other);
999 void InferRange(HValue* value); 1002 void InferRange(HValue* value);
1000 void RollBackTo(int index); 1003 void RollBackTo(int index);
(...skipping 124 matching lines...)
1125 for (int i = index + 1; i < changed_ranges_.length(); ++i) { 1128 for (int i = index + 1; i < changed_ranges_.length(); ++i) {
1126 changed_ranges_[i]->RemoveLastAddedRange(); 1129 changed_ranges_[i]->RemoveLastAddedRange();
1127 } 1130 }
1128 changed_ranges_.Rewind(index + 1); 1131 changed_ranges_.Rewind(index + 1);
1129 } 1132 }
1130 1133
1131 1134
1132 void HRangeAnalysis::AddRange(HValue* value, Range* range) { 1135 void HRangeAnalysis::AddRange(HValue* value, Range* range) {
1133 Range* original_range = value->range(); 1136 Range* original_range = value->range();
1134 value->AddNewRange(range, zone_); 1137 value->AddNewRange(range, zone_);
1135 changed_ranges_.Add(value); 1138 changed_ranges_.Add(value, zone_);
1136 Range* new_range = value->range(); 1139 Range* new_range = value->range();
1137 TraceRange("Updated range of %d set to [%d,%d]\n", 1140 TraceRange("Updated range of %d set to [%d,%d]\n",
1138 value->id(), 1141 value->id(),
1139 new_range->lower(), 1142 new_range->lower(),
1140 new_range->upper()); 1143 new_range->upper());
1141 if (original_range != NULL) { 1144 if (original_range != NULL) {
1142 TraceRange("Original range was [%d,%d]\n", 1145 TraceRange("Original range was [%d,%d]\n",
1143 original_range->lower(), 1146 original_range->lower(),
1144 original_range->upper()); 1147 original_range->upper());
1145 } 1148 }
(...skipping 107 matching lines...)
1253 int next = array_[pos].next; 1256 int next = array_[pos].next;
1254 while (next != kNil) { 1257 while (next != kNil) {
1255 if (lists_[next].value->Equals(value)) return lists_[next].value; 1258 if (lists_[next].value->Equals(value)) return lists_[next].value;
1256 next = lists_[next].next; 1259 next = lists_[next].next;
1257 } 1260 }
1258 } 1261 }
1259 return NULL; 1262 return NULL;
1260 } 1263 }
1261 1264
1262 1265
1263 void HValueMap::Resize(int new_size) { 1266 void HValueMap::Resize(int new_size, Zone* zone) {
1264 ASSERT(new_size > count_); 1267 ASSERT(new_size > count_);
1265 // Hashing the values into the new array has no more collisions than in the 1268 // Hashing the values into the new array has no more collisions than in the
1266 // old hash map, so we can use the existing lists_ array, if we are careful. 1269 // old hash map, so we can use the existing lists_ array, if we are careful.
1267 1270
1268 // Make sure we have at least one free element. 1271 // Make sure we have at least one free element.
1269 if (free_list_head_ == kNil) { 1272 if (free_list_head_ == kNil) {
1270 ResizeLists(lists_size_ << 1); 1273 ResizeLists(lists_size_ << 1, zone);
1271 } 1274 }
1272 1275
1273 HValueMapListElement* new_array = 1276 HValueMapListElement* new_array =
1274 ZONE->NewArray<HValueMapListElement>(new_size); 1277 zone->NewArray<HValueMapListElement>(new_size);
1275 memset(new_array, 0, sizeof(HValueMapListElement) * new_size); 1278 memset(new_array, 0, sizeof(HValueMapListElement) * new_size);
1276 1279
1277 HValueMapListElement* old_array = array_; 1280 HValueMapListElement* old_array = array_;
1278 int old_size = array_size_; 1281 int old_size = array_size_;
1279 1282
1280 int old_count = count_; 1283 int old_count = count_;
1281 count_ = 0; 1284 count_ = 0;
1282 // Do not modify present_flags_. It is currently correct. 1285 // Do not modify present_flags_. It is currently correct.
1283 array_size_ = new_size; 1286 array_size_ = new_size;
1284 array_ = new_array; 1287 array_ = new_array;
1285 1288
1286 if (old_array != NULL) { 1289 if (old_array != NULL) {
1287 // Iterate over all the elements in lists, rehashing them. 1290 // Iterate over all the elements in lists, rehashing them.
1288 for (int i = 0; i < old_size; ++i) { 1291 for (int i = 0; i < old_size; ++i) {
1289 if (old_array[i].value != NULL) { 1292 if (old_array[i].value != NULL) {
1290 int current = old_array[i].next; 1293 int current = old_array[i].next;
1291 while (current != kNil) { 1294 while (current != kNil) {
1292 Insert(lists_[current].value); 1295 Insert(lists_[current].value, zone);
1293 int next = lists_[current].next; 1296 int next = lists_[current].next;
1294 lists_[current].next = free_list_head_; 1297 lists_[current].next = free_list_head_;
1295 free_list_head_ = current; 1298 free_list_head_ = current;
1296 current = next; 1299 current = next;
1297 } 1300 }
1298 // Rehash the directly stored value. 1301 // Rehash the directly stored value.
1299 Insert(old_array[i].value); 1302 Insert(old_array[i].value, zone);
1300 } 1303 }
1301 } 1304 }
1302 } 1305 }
1303 USE(old_count); 1306 USE(old_count);
1304 ASSERT(count_ == old_count); 1307 ASSERT(count_ == old_count);
1305 } 1308 }
1306 1309
1307 1310
1308 void HValueMap::ResizeLists(int new_size) { 1311 void HValueMap::ResizeLists(int new_size, Zone* zone) {
1309 ASSERT(new_size > lists_size_); 1312 ASSERT(new_size > lists_size_);
1310 1313
1311 HValueMapListElement* new_lists = 1314 HValueMapListElement* new_lists =
1312 ZONE->NewArray<HValueMapListElement>(new_size); 1315 zone->NewArray<HValueMapListElement>(new_size);
1313 memset(new_lists, 0, sizeof(HValueMapListElement) * new_size); 1316 memset(new_lists, 0, sizeof(HValueMapListElement) * new_size);
1314 1317
1315 HValueMapListElement* old_lists = lists_; 1318 HValueMapListElement* old_lists = lists_;
1316 int old_size = lists_size_; 1319 int old_size = lists_size_;
1317 1320
1318 lists_size_ = new_size; 1321 lists_size_ = new_size;
1319 lists_ = new_lists; 1322 lists_ = new_lists;
1320 1323
1321 if (old_lists != NULL) { 1324 if (old_lists != NULL) {
1322 memcpy(lists_, old_lists, old_size * sizeof(HValueMapListElement)); 1325 memcpy(lists_, old_lists, old_size * sizeof(HValueMapListElement));
1323 } 1326 }
1324 for (int i = old_size; i < lists_size_; ++i) { 1327 for (int i = old_size; i < lists_size_; ++i) {
1325 lists_[i].next = free_list_head_; 1328 lists_[i].next = free_list_head_;
1326 free_list_head_ = i; 1329 free_list_head_ = i;
1327 } 1330 }
1328 } 1331 }
1329 1332
1330 1333
1331 void HValueMap::Insert(HValue* value) { 1334 void HValueMap::Insert(HValue* value, Zone* zone) {
1332 ASSERT(value != NULL); 1335 ASSERT(value != NULL);
1333 // Resizing when half of the hashtable is filled up. 1336 // Resizing when half of the hashtable is filled up.
1334 if (count_ >= array_size_ >> 1) Resize(array_size_ << 1); 1337 if (count_ >= array_size_ >> 1) Resize(array_size_ << 1, zone);
1335 ASSERT(count_ < array_size_); 1338 ASSERT(count_ < array_size_);
1336 count_++; 1339 count_++;
1337 uint32_t pos = Bound(static_cast<uint32_t>(value->Hashcode())); 1340 uint32_t pos = Bound(static_cast<uint32_t>(value->Hashcode()));
1338 if (array_[pos].value == NULL) { 1341 if (array_[pos].value == NULL) {
1339 array_[pos].value = value; 1342 array_[pos].value = value;
1340 array_[pos].next = kNil; 1343 array_[pos].next = kNil;
1341 } else { 1344 } else {
1342 if (free_list_head_ == kNil) { 1345 if (free_list_head_ == kNil) {
1343 ResizeLists(lists_size_ << 1); 1346 ResizeLists(lists_size_ << 1, zone);
1344 } 1347 }
1345 int new_element_pos = free_list_head_; 1348 int new_element_pos = free_list_head_;
1346 ASSERT(new_element_pos != kNil); 1349 ASSERT(new_element_pos != kNil);
1347 free_list_head_ = lists_[free_list_head_].next; 1350 free_list_head_ = lists_[free_list_head_].next;
1348 lists_[new_element_pos].value = value; 1351 lists_[new_element_pos].value = value;
1349 lists_[new_element_pos].next = array_[pos].next; 1352 lists_[new_element_pos].next = array_[pos].next;
1350 ASSERT(array_[pos].next == kNil || lists_[array_[pos].next].value != NULL); 1353 ASSERT(array_[pos].next == kNil || lists_[array_[pos].next].value != NULL);
1351 array_[pos].next = new_element_pos; 1354 array_[pos].next = new_element_pos;
1352 } 1355 }
1353 } 1356 }
(...skipping 117 matching lines...)
1471 DISALLOW_COPY_AND_ASSIGN(SparseSet); 1474 DISALLOW_COPY_AND_ASSIGN(SparseSet);
1472 }; 1475 };
1473 1476
1474 1477
1475 class HGlobalValueNumberer BASE_EMBEDDED { 1478 class HGlobalValueNumberer BASE_EMBEDDED {
1476 public: 1479 public:
1477 explicit HGlobalValueNumberer(HGraph* graph, CompilationInfo* info) 1480 explicit HGlobalValueNumberer(HGraph* graph, CompilationInfo* info)
1478 : graph_(graph), 1481 : graph_(graph),
1479 info_(info), 1482 info_(info),
1480 removed_side_effects_(false), 1483 removed_side_effects_(false),
1481 block_side_effects_(graph->blocks()->length()), 1484 block_side_effects_(graph->blocks()->length(), graph->zone()),
1482 loop_side_effects_(graph->blocks()->length()), 1485 loop_side_effects_(graph->blocks()->length(), graph->zone()),
1483 visited_on_paths_(graph->zone(), graph->blocks()->length()) { 1486 visited_on_paths_(graph->zone(), graph->blocks()->length()) {
1484 ASSERT(info->isolate()->heap()->allow_allocation(false)); 1487 ASSERT(info->isolate()->heap()->allow_allocation(false));
1485 block_side_effects_.AddBlock(GVNFlagSet(), graph_->blocks()->length()); 1488 block_side_effects_.AddBlock(GVNFlagSet(), graph_->blocks()->length(),
1486 loop_side_effects_.AddBlock(GVNFlagSet(), graph_->blocks()->length()); 1489 graph_->zone());
1490 loop_side_effects_.AddBlock(GVNFlagSet(), graph_->blocks()->length(),
1491 graph_->zone());
1487 } 1492 }
1488 ~HGlobalValueNumberer() { 1493 ~HGlobalValueNumberer() {
1489 ASSERT(!info_->isolate()->heap()->allow_allocation(true)); 1494 ASSERT(!info_->isolate()->heap()->allow_allocation(true));
1490 } 1495 }
1491 1496
1492 // Returns true if values with side effects are removed. 1497 // Returns true if values with side effects are removed.
1493 bool Analyze(); 1498 bool Analyze();
1494 1499
1495 private: 1500 private:
1496 GVNFlagSet CollectSideEffectsOnPathsToDominatedBlock( 1501 GVNFlagSet CollectSideEffectsOnPathsToDominatedBlock(
(...skipping 445 matching lines...)
1942 int dominated_index_; 1947 int dominated_index_;
1943 int length_; 1948 int length_;
1944 }; 1949 };
1945 1950
1946 // This is a recursive traversal of the dominator tree but it has been turned 1951 // This is a recursive traversal of the dominator tree but it has been turned
1947 // into a loop to avoid stack overflows. 1952 // into a loop to avoid stack overflows.
1948 // The logical "stack frames" of the recursion are kept in a list of 1953 // The logical "stack frames" of the recursion are kept in a list of
1949 // GvnBasicBlockState instances. 1954 // GvnBasicBlockState instances.
1950 void HGlobalValueNumberer::AnalyzeGraph() { 1955 void HGlobalValueNumberer::AnalyzeGraph() {
1951 HBasicBlock* entry_block = graph_->entry_block(); 1956 HBasicBlock* entry_block = graph_->entry_block();
1952 HValueMap* entry_map = new(zone()) HValueMap(); 1957 HValueMap* entry_map = new(zone()) HValueMap(zone());
1953 GvnBasicBlockState* current = 1958 GvnBasicBlockState* current =
1954 GvnBasicBlockState::CreateEntry(zone(), entry_block, entry_map); 1959 GvnBasicBlockState::CreateEntry(zone(), entry_block, entry_map);
1955 1960
1956 while (current != NULL) { 1961 while (current != NULL) {
1957 HBasicBlock* block = current->block(); 1962 HBasicBlock* block = current->block();
1958 HValueMap* map = current->map(); 1963 HValueMap* map = current->map();
1959 HSideEffectMap* dominators = current->dominators(); 1964 HSideEffectMap* dominators = current->dominators();
1960 1965
1961 TRACE_GVN_2("Analyzing block B%d%s\n", 1966 TRACE_GVN_2("Analyzing block B%d%s\n",
1962 block->block_id(), 1967 block->block_id(),
(...skipping 23 matching lines...)
1986 if (other != NULL) { 1991 if (other != NULL) {
1987 ASSERT(instr->Equals(other) && other->Equals(instr)); 1992 ASSERT(instr->Equals(other) && other->Equals(instr));
1988 TRACE_GVN_4("Replacing value %d (%s) with value %d (%s)\n", 1993 TRACE_GVN_4("Replacing value %d (%s) with value %d (%s)\n",
1989 instr->id(), 1994 instr->id(),
1990 instr->Mnemonic(), 1995 instr->Mnemonic(),
1991 other->id(), 1996 other->id(),
1992 other->Mnemonic()); 1997 other->Mnemonic());
1993 if (instr->HasSideEffects()) removed_side_effects_ = true; 1998 if (instr->HasSideEffects()) removed_side_effects_ = true;
1994 instr->DeleteAndReplaceWith(other); 1999 instr->DeleteAndReplaceWith(other);
1995 } else { 2000 } else {
1996 map->Add(instr); 2001 map->Add(instr, zone());
1997 } 2002 }
1998 } 2003 }
1999 if (instr->CheckFlag(HValue::kTrackSideEffectDominators)) { 2004 if (instr->CheckFlag(HValue::kTrackSideEffectDominators)) {
2000 for (int i = 0; i < kNumberOfTrackedSideEffects; i++) { 2005 for (int i = 0; i < kNumberOfTrackedSideEffects; i++) {
2001 HValue* other = dominators->at(i); 2006 HValue* other = dominators->at(i);
2002 GVNFlag changes_flag = HValue::ChangesFlagFromInt(i); 2007 GVNFlag changes_flag = HValue::ChangesFlagFromInt(i);
2003 GVNFlag depends_on_flag = HValue::DependsOnFlagFromInt(i); 2008 GVNFlag depends_on_flag = HValue::DependsOnFlagFromInt(i);
2004 if (instr->DependsOnFlags().Contains(depends_on_flag) && 2009 if (instr->DependsOnFlags().Contains(depends_on_flag) &&
2005 (other != NULL)) { 2010 (other != NULL)) {
2006 TRACE_GVN_5("Side-effect #%d in %d (%s) is dominated by %d (%s)\n", 2011 TRACE_GVN_5("Side-effect #%d in %d (%s) is dominated by %d (%s)\n",
(...skipping 35 matching lines...)
2042 } 2047 }
2043 current = next; 2048 current = next;
2044 } 2049 }
2045 } 2050 }
2046 2051
2047 2052
2048 class HInferRepresentation BASE_EMBEDDED { 2053 class HInferRepresentation BASE_EMBEDDED {
2049 public: 2054 public:
2050 explicit HInferRepresentation(HGraph* graph) 2055 explicit HInferRepresentation(HGraph* graph)
2051 : graph_(graph), 2056 : graph_(graph),
2052 worklist_(8), 2057 worklist_(8, graph->zone()),
2053 in_worklist_(graph->GetMaximumValueID(), graph->zone()) { } 2058 in_worklist_(graph->GetMaximumValueID(), graph->zone()) { }
2054 2059
2055 void Analyze(); 2060 void Analyze();
2056 2061
2057 private: 2062 private:
2058 Representation TryChange(HValue* current); 2063 Representation TryChange(HValue* current);
2059 void AddToWorklist(HValue* current); 2064 void AddToWorklist(HValue* current);
2060 void InferBasedOnInputs(HValue* current); 2065 void InferBasedOnInputs(HValue* current);
2061 void AddDependantsToWorklist(HValue* current); 2066 void AddDependantsToWorklist(HValue* current);
2062 void InferBasedOnUses(HValue* current); 2067 void InferBasedOnUses(HValue* current);
2063 2068
2064 Zone* zone() { return graph_->zone(); } 2069 Zone* zone() { return graph_->zone(); }
2065 2070
2066 HGraph* graph_; 2071 HGraph* graph_;
2067 ZoneList<HValue*> worklist_; 2072 ZoneList<HValue*> worklist_;
2068 BitVector in_worklist_; 2073 BitVector in_worklist_;
2069 }; 2074 };
2070 2075
2071 2076
2072 void HInferRepresentation::AddToWorklist(HValue* current) { 2077 void HInferRepresentation::AddToWorklist(HValue* current) {
2073 if (current->representation().IsSpecialization()) return; 2078 if (current->representation().IsSpecialization()) return;
2074 if (!current->CheckFlag(HValue::kFlexibleRepresentation)) return; 2079 if (!current->CheckFlag(HValue::kFlexibleRepresentation)) return;
2075 if (in_worklist_.Contains(current->id())) return; 2080 if (in_worklist_.Contains(current->id())) return;
2076 worklist_.Add(current); 2081 worklist_.Add(current, zone());
2077 in_worklist_.Add(current->id()); 2082 in_worklist_.Add(current->id());
2078 } 2083 }
2079 2084
2080 2085
2081 // This method tries to specialize the representation type of the value 2086 // This method tries to specialize the representation type of the value
2082 // given as a parameter. The value is asked to infer its representation type 2087 // given as a parameter. The value is asked to infer its representation type
2083 // based on its inputs. If the inferred type is more specialized, then this 2088 // based on its inputs. If the inferred type is more specialized, then this
2084 // becomes the new representation type of the node. 2089 // becomes the new representation type of the node.
2085 void HInferRepresentation::InferBasedOnInputs(HValue* current) { 2090 void HInferRepresentation::InferBasedOnInputs(HValue* current) {
2086 Representation r = current->representation(); 2091 Representation r = current->representation();
(...skipping 82 matching lines...)
2169 } 2174 }
2170 2175
2171 2176
2172 void HInferRepresentation::Analyze() { 2177 void HInferRepresentation::Analyze() {
2173 HPhase phase("H_Infer representations", graph_); 2178 HPhase phase("H_Infer representations", graph_);
2174 2179
2175 // (1) Initialize bit vectors and count real uses. Each phi gets a 2180 // (1) Initialize bit vectors and count real uses. Each phi gets a
2176 // bit-vector of length <number of phis>. 2181 // bit-vector of length <number of phis>.
2177 const ZoneList<HPhi*>* phi_list = graph_->phi_list(); 2182 const ZoneList<HPhi*>* phi_list = graph_->phi_list();
2178 int phi_count = phi_list->length(); 2183 int phi_count = phi_list->length();
2179 ZoneList<BitVector*> connected_phis(phi_count); 2184 ZoneList<BitVector*> connected_phis(phi_count, graph_->zone());
2180 for (int i = 0; i < phi_count; ++i) { 2185 for (int i = 0; i < phi_count; ++i) {
2181 phi_list->at(i)->InitRealUses(i); 2186 phi_list->at(i)->InitRealUses(i);
2182 BitVector* connected_set = new(zone()) BitVector(phi_count, graph_->zone()); 2187 BitVector* connected_set = new(zone()) BitVector(phi_count, graph_->zone());
2183 connected_set->Add(i); 2188 connected_set->Add(i);
2184 connected_phis.Add(connected_set); 2189 connected_phis.Add(connected_set, zone());
2185 } 2190 }
2186 2191
2187 // (2) Do a fixed point iteration to find the set of connected phis. A 2192 // (2) Do a fixed point iteration to find the set of connected phis. A
2188 // phi is connected to another phi if its value is used either directly or 2193 // phi is connected to another phi if its value is used either directly or
2189 // indirectly through a transitive closure of the def-use relation. 2194 // indirectly through a transitive closure of the def-use relation.
2190 bool change = true; 2195 bool change = true;
2191 while (change) { 2196 while (change) {
2192 change = false; 2197 change = false;
2193 // We normally have far more "forward edges" than "backward edges", 2198 // We normally have far more "forward edges" than "backward edges",
2194 // so we terminate faster when we walk backwards. 2199 // so we terminate faster when we walk backwards.
(...skipping 75 matching lines...)
2270 } 2275 }
2271 2276
2272 if (block->IsLoopHeader()) { 2277 if (block->IsLoopHeader()) {
2273 HBasicBlock* last_back_edge = 2278 HBasicBlock* last_back_edge =
2274 block->loop_information()->GetLastBackEdge(); 2279 block->loop_information()->GetLastBackEdge();
2275 InitializeInferredTypes(i + 1, last_back_edge->block_id()); 2280 InitializeInferredTypes(i + 1, last_back_edge->block_id());
2276 // Skip all blocks already processed by the recursive call. 2281 // Skip all blocks already processed by the recursive call.
2277 i = last_back_edge->block_id(); 2282 i = last_back_edge->block_id();
2278 // Update phis of the loop header now after the whole loop body is 2283 // Update phis of the loop header now after the whole loop body is
2279 // guaranteed to be processed. 2284 // guaranteed to be processed.
2280 ZoneList<HValue*> worklist(block->phis()->length()); 2285 ZoneList<HValue*> worklist(block->phis()->length(), zone());
2281 for (int j = 0; j < block->phis()->length(); ++j) { 2286 for (int j = 0; j < block->phis()->length(); ++j) {
2282 worklist.Add(block->phis()->at(j)); 2287 worklist.Add(block->phis()->at(j), zone());
2283 } 2288 }
2284 InferTypes(&worklist); 2289 InferTypes(&worklist);
2285 } 2290 }
2286 } 2291 }
2287 } 2292 }
2288 2293
2289 2294
2290 void HGraph::PropagateMinusZeroChecks(HValue* value, BitVector* visited) { 2295 void HGraph::PropagateMinusZeroChecks(HValue* value, BitVector* visited) {
2291 HValue* current = value; 2296 HValue* current = value;
2292 while (current != NULL) { 2297 while (current != NULL) {
(...skipping 46 matching lines...)
2339 // information we treat constants like normal instructions and insert the 2344 // information we treat constants like normal instructions and insert the
2340 // change instructions for them. 2345 // change instructions for them.
2341 HInstruction* new_value = NULL; 2346 HInstruction* new_value = NULL;
2342 bool is_truncating = use_value->CheckFlag(HValue::kTruncatingToInt32); 2347 bool is_truncating = use_value->CheckFlag(HValue::kTruncatingToInt32);
2343 bool deoptimize_on_undefined = 2348 bool deoptimize_on_undefined =
2344 use_value->CheckFlag(HValue::kDeoptimizeOnUndefined); 2349 use_value->CheckFlag(HValue::kDeoptimizeOnUndefined);
2345 if (value->IsConstant()) { 2350 if (value->IsConstant()) {
2346 HConstant* constant = HConstant::cast(value); 2351 HConstant* constant = HConstant::cast(value);
2347 // Try to create a new copy of the constant with the new representation. 2352 // Try to create a new copy of the constant with the new representation.
2348 new_value = is_truncating 2353 new_value = is_truncating
2349 ? constant->CopyToTruncatedInt32() 2354 ? constant->CopyToTruncatedInt32(zone())
2350 : constant->CopyToRepresentation(to); 2355 : constant->CopyToRepresentation(to, zone());
2351 } 2356 }
2352 2357
2353 if (new_value == NULL) { 2358 if (new_value == NULL) {
2354 new_value = new(zone()) HChange(value, to, 2359 new_value = new(zone()) HChange(value, to,
2355 is_truncating, deoptimize_on_undefined); 2360 is_truncating, deoptimize_on_undefined);
2356 } 2361 }
2357 2362
2358 new_value->InsertBefore(next); 2363 new_value->InsertBefore(next);
2359 use_value->SetOperandAt(use_index, new_value); 2364 use_value->SetOperandAt(use_index, new_value);
2360 } 2365 }
(...skipping 398 matching lines...)
2759 2764
2760 2765
2761 void HGraphBuilder::VisitExpressions(ZoneList<Expression*>* exprs) { 2766 void HGraphBuilder::VisitExpressions(ZoneList<Expression*>* exprs) {
2762 for (int i = 0; i < exprs->length(); ++i) { 2767 for (int i = 0; i < exprs->length(); ++i) {
2763 CHECK_ALIVE(VisitForValue(exprs->at(i))); 2768 CHECK_ALIVE(VisitForValue(exprs->at(i)));
2764 } 2769 }
2765 } 2770 }
2766 2771
2767 2772
2768 HGraph* HGraphBuilder::CreateGraph() { 2773 HGraph* HGraphBuilder::CreateGraph() {
2769 graph_ = new(zone()) HGraph(info()); 2774 graph_ = new(zone()) HGraph(info(), zone());
2770 if (FLAG_hydrogen_stats) HStatistics::Instance()->Initialize(info()); 2775 if (FLAG_hydrogen_stats) HStatistics::Instance()->Initialize(info());
2771 2776
2772 { 2777 {
2773 HPhase phase("H_Block building"); 2778 HPhase phase("H_Block building");
2774 current_block_ = graph()->entry_block(); 2779 current_block_ = graph()->entry_block();
2775 2780
2776 Scope* scope = info()->scope(); 2781 Scope* scope = info()->scope();
2777 if (scope->HasIllegalRedeclaration()) { 2782 if (scope->HasIllegalRedeclaration()) {
2778 Bailout("function with illegal redeclaration"); 2783 Bailout("function with illegal redeclaration");
2779 return NULL; 2784 return NULL;
(...skipping 330 matching lines...)
3110 3115
3111 static bool BoundsCheckKeyMatch(void* key1, void* key2) { 3116 static bool BoundsCheckKeyMatch(void* key1, void* key2) {
3112 BoundsCheckKey* k1 = static_cast<BoundsCheckKey*>(key1); 3117 BoundsCheckKey* k1 = static_cast<BoundsCheckKey*>(key1);
3113 BoundsCheckKey* k2 = static_cast<BoundsCheckKey*>(key2); 3118 BoundsCheckKey* k2 = static_cast<BoundsCheckKey*>(key2);
3114 return k1->IndexBase() == k2->IndexBase() && k1->Length() == k2->Length(); 3119 return k1->IndexBase() == k2->IndexBase() && k1->Length() == k2->Length();
3115 } 3120 }
3116 3121
3117 3122
3118 class BoundsCheckTable : private ZoneHashMap { 3123 class BoundsCheckTable : private ZoneHashMap {
3119 public: 3124 public:
3120 BoundsCheckBbData** LookupOrInsert(BoundsCheckKey* key) { 3125 BoundsCheckBbData** LookupOrInsert(BoundsCheckKey* key, Zone* zone) {
3121 return reinterpret_cast<BoundsCheckBbData**>( 3126 return reinterpret_cast<BoundsCheckBbData**>(
3122 &(Lookup(key, key->Hash(), true)->value)); 3127 &(Lookup(key, key->Hash(), true, ZoneAllocationPolicy(zone))->value));
3123 } 3128 }
3124 3129
3125 void Insert(BoundsCheckKey* key, BoundsCheckBbData* data) { 3130 void Insert(BoundsCheckKey* key, BoundsCheckBbData* data, Zone* zone) {
3126 Lookup(key, key->Hash(), true)->value = data; 3131 Lookup(key, key->Hash(), true, ZoneAllocationPolicy(zone))->value = data;
3127 } 3132 }
3128 3133
3129 void Delete(BoundsCheckKey* key) { 3134 void Delete(BoundsCheckKey* key) {
3130 Remove(key, key->Hash()); 3135 Remove(key, key->Hash());
3131 } 3136 }
3132 3137
3133 BoundsCheckTable() : ZoneHashMap(BoundsCheckKeyMatch) { } 3138 explicit BoundsCheckTable(Zone* zone) : ZoneHashMap(BoundsCheckKeyMatch, 8,
danno 2012/06/05 13:42:35 Make this a shared constant. Also, weird formattin
sanjoy 2012/06/05 14:21:39 Fixed.
3139 ZoneAllocationPolicy(
3140 zone)) { }
3134 }; 3141 };
3135 3142
3136 3143
3137 // Eliminates checks in bb and recursively in the dominated blocks. 3144 // Eliminates checks in bb and recursively in the dominated blocks.
3138 // Also replace the results of check instructions with the original value, if 3145 // Also replace the results of check instructions with the original value, if
3139 // the result is used. This is safe now, since we don't do code motion after 3146 // the result is used. This is safe now, since we don't do code motion after
3140 // this point. It enables better register allocation since the value produced 3147 // this point. It enables better register allocation since the value produced
3141 // by check instructions is really a copy of the original value. 3148 // by check instructions is really a copy of the original value.
3142 void HGraph::EliminateRedundantBoundsChecks(HBasicBlock* bb, 3149 void HGraph::EliminateRedundantBoundsChecks(HBasicBlock* bb,
3143 BoundsCheckTable* table) { 3150 BoundsCheckTable* table) {
3144 BoundsCheckBbData* bb_data_list = NULL; 3151 BoundsCheckBbData* bb_data_list = NULL;
3145 3152
3146 for (HInstruction* i = bb->first(); i != NULL; i = i->next()) { 3153 for (HInstruction* i = bb->first(); i != NULL; i = i->next()) {
3147 if (!i->IsBoundsCheck()) continue; 3154 if (!i->IsBoundsCheck()) continue;
3148 3155
3149 HBoundsCheck* check = HBoundsCheck::cast(i); 3156 HBoundsCheck* check = HBoundsCheck::cast(i);
3150 check->ReplaceAllUsesWith(check->index()); 3157 check->ReplaceAllUsesWith(check->index());
3151 3158
3152 if (!FLAG_array_bounds_checks_elimination) continue; 3159 if (!FLAG_array_bounds_checks_elimination) continue;
3153 3160
3154 int32_t offset; 3161 int32_t offset;
3155 BoundsCheckKey* key = 3162 BoundsCheckKey* key =
3156 BoundsCheckKey::Create(bb->zone(), check, &offset); 3163 BoundsCheckKey::Create(zone(), check, &offset);
3157 BoundsCheckBbData** data_p = table->LookupOrInsert(key); 3164 BoundsCheckBbData** data_p = table->LookupOrInsert(key, zone());
3158 BoundsCheckBbData* data = *data_p; 3165 BoundsCheckBbData* data = *data_p;
3159 if (data == NULL) { 3166 if (data == NULL) {
3160 bb_data_list = new(zone()) BoundsCheckBbData(key, 3167 bb_data_list = new(zone()) BoundsCheckBbData(key,
3161 offset, 3168 offset,
3162 offset, 3169 offset,
3163 bb, 3170 bb,
3164 check, 3171 check,
3165 bb_data_list, 3172 bb_data_list,
3166 NULL); 3173 NULL);
3167 *data_p = bb_data_list; 3174 *data_p = bb_data_list;
3168 } else if (data->OffsetIsCovered(offset)) { 3175 } else if (data->OffsetIsCovered(offset)) {
3169 check->DeleteAndReplaceWith(NULL); 3176 check->DeleteAndReplaceWith(NULL);
3170 } else if (data->BasicBlock() == bb) { 3177 } else if (data->BasicBlock() == bb) {
3171 data->CoverCheck(check, offset); 3178 data->CoverCheck(check, offset);
3172 } else { 3179 } else {
3173 int32_t new_lower_offset = offset < data->LowerOffset() 3180 int32_t new_lower_offset = offset < data->LowerOffset()
3174 ? offset 3181 ? offset
3175 : data->LowerOffset(); 3182 : data->LowerOffset();
3176 int32_t new_upper_offset = offset > data->UpperOffset() 3183 int32_t new_upper_offset = offset > data->UpperOffset()
3177 ? offset 3184 ? offset
3178 : data->UpperOffset(); 3185 : data->UpperOffset();
3179 bb_data_list = new(bb->zone()) BoundsCheckBbData(key, 3186 bb_data_list = new(zone()) BoundsCheckBbData(key,
3180 new_lower_offset, 3187 new_lower_offset,
3181 new_upper_offset, 3188 new_upper_offset,
3182 bb, 3189 bb,
3183 check, 3190 check,
3184 bb_data_list, 3191 bb_data_list,
3185 data); 3192 data);
3186 table->Insert(key, bb_data_list); 3193 table->Insert(key, bb_data_list, zone());
3187 } 3194 }
3188 } 3195 }
3189 3196
3190 for (int i = 0; i < bb->dominated_blocks()->length(); ++i) { 3197 for (int i = 0; i < bb->dominated_blocks()->length(); ++i) {
3191 EliminateRedundantBoundsChecks(bb->dominated_blocks()->at(i), table); 3198 EliminateRedundantBoundsChecks(bb->dominated_blocks()->at(i), table);
3192 } 3199 }
3193 3200
3194 for (BoundsCheckBbData* data = bb_data_list; 3201 for (BoundsCheckBbData* data = bb_data_list;
3195 data != NULL; 3202 data != NULL;
3196 data = data->NextInBasicBlock()) { 3203 data = data->NextInBasicBlock()) {
3197 data->RemoveZeroOperations(); 3204 data->RemoveZeroOperations();
3198 if (data->FatherInDominatorTree()) { 3205 if (data->FatherInDominatorTree()) {
3199 table->Insert(data->Key(), data->FatherInDominatorTree()); 3206 table->Insert(data->Key(), data->FatherInDominatorTree(), zone());
3200 } else { 3207 } else {
3201 table->Delete(data->Key()); 3208 table->Delete(data->Key());
3202 } 3209 }
3203 } 3210 }
3204 } 3211 }
3205 3212
3206 3213
3207 void HGraph::EliminateRedundantBoundsChecks() { 3214 void HGraph::EliminateRedundantBoundsChecks() {
3208 HPhase phase("H_Eliminate bounds checks", this); 3215 HPhase phase("H_Eliminate bounds checks", this);
3209 AssertNoAllocation no_gc; 3216 AssertNoAllocation no_gc;
3210 BoundsCheckTable checks_table; 3217 BoundsCheckTable checks_table(zone());
3211 EliminateRedundantBoundsChecks(entry_block(), &checks_table); 3218 EliminateRedundantBoundsChecks(entry_block(), &checks_table);
3212 } 3219 }
3213 3220
3214 3221
3215 static void DehoistArrayIndex(ArrayInstructionInterface* array_operation) { 3222 static void DehoistArrayIndex(ArrayInstructionInterface* array_operation) {
3216 HValue* index = array_operation->GetKey(); 3223 HValue* index = array_operation->GetKey();
3217 3224
3218 HConstant* constant; 3225 HConstant* constant;
3219 HValue* subexpression; 3226 HValue* subexpression;
3220 int32_t sign; 3227 int32_t sign;
(...skipping 99 matching lines...)
3320 3327
3321 void HGraphBuilder::PushAndAdd(HInstruction* instr) { 3328 void HGraphBuilder::PushAndAdd(HInstruction* instr) {
3322 Push(instr); 3329 Push(instr);
3323 AddInstruction(instr); 3330 AddInstruction(instr);
3324 } 3331 }
3325 3332
3326 3333
3327 template <class Instruction> 3334 template <class Instruction>
3328 HInstruction* HGraphBuilder::PreProcessCall(Instruction* call) { 3335 HInstruction* HGraphBuilder::PreProcessCall(Instruction* call) {
3329 int count = call->argument_count(); 3336 int count = call->argument_count();
3330 ZoneList<HValue*> arguments(count); 3337 ZoneList<HValue*> arguments(count, zone());
3331 for (int i = 0; i < count; ++i) { 3338 for (int i = 0; i < count; ++i) {
3332 arguments.Add(Pop()); 3339 arguments.Add(Pop(), zone());
3333 } 3340 }
3334 3341
3335 while (!arguments.is_empty()) { 3342 while (!arguments.is_empty()) {
3336 AddInstruction(new(zone()) HPushArgument(arguments.RemoveLast())); 3343 AddInstruction(new(zone()) HPushArgument(arguments.RemoveLast()));
3337 } 3344 }
3338 return call; 3345 return call;
3339 } 3346 }
3340 3347
3341 3348
3342 void HGraphBuilder::SetUpScope(Scope* scope) { 3349 void HGraphBuilder::SetUpScope(Scope* scope) {
(...skipping 479 matching lines...)
3822 current_block()->Finish(test); 3829 current_block()->Finish(test);
3823 3830
3824 HBasicBlock* loop_predecessor = graph()->CreateBasicBlock(); 3831 HBasicBlock* loop_predecessor = graph()->CreateBasicBlock();
3825 non_osr_entry->Goto(loop_predecessor); 3832 non_osr_entry->Goto(loop_predecessor);
3826 3833
3827 set_current_block(osr_entry); 3834 set_current_block(osr_entry);
3828 int osr_entry_id = statement->OsrEntryId(); 3835 int osr_entry_id = statement->OsrEntryId();
3829 int first_expression_index = environment()->first_expression_index(); 3836 int first_expression_index = environment()->first_expression_index();
3830 int length = environment()->length(); 3837 int length = environment()->length();
3831 ZoneList<HUnknownOSRValue*>* osr_values = 3838 ZoneList<HUnknownOSRValue*>* osr_values =
3832 new(zone()) ZoneList<HUnknownOSRValue*>(length); 3839 new(zone()) ZoneList<HUnknownOSRValue*>(length, zone());
3833 3840
3834 for (int i = 0; i < first_expression_index; ++i) { 3841 for (int i = 0; i < first_expression_index; ++i) {
3835 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue; 3842 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue;
3836 AddInstruction(osr_value); 3843 AddInstruction(osr_value);
3837 environment()->Bind(i, osr_value); 3844 environment()->Bind(i, osr_value);
3838 osr_values->Add(osr_value); 3845 osr_values->Add(osr_value, zone());
3839 } 3846 }
3840 3847
3841 if (first_expression_index != length) { 3848 if (first_expression_index != length) {
3842 environment()->Drop(length - first_expression_index); 3849 environment()->Drop(length - first_expression_index);
3843 for (int i = first_expression_index; i < length; ++i) { 3850 for (int i = first_expression_index; i < length; ++i) {
3844 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue; 3851 HUnknownOSRValue* osr_value = new(zone()) HUnknownOSRValue;
3845 AddInstruction(osr_value); 3852 AddInstruction(osr_value);
3846 environment()->Push(osr_value); 3853 environment()->Push(osr_value);
3847 osr_values->Add(osr_value); 3854 osr_values->Add(osr_value, zone());
3848 } 3855 }
3849 } 3856 }
3850 3857
3851 graph()->set_osr_values(osr_values); 3858 graph()->set_osr_values(osr_values);
3852 3859
3853 AddSimulate(osr_entry_id); 3860 AddSimulate(osr_entry_id);
3854 AddInstruction(new(zone()) HOsrEntry(osr_entry_id)); 3861 AddInstruction(new(zone()) HOsrEntry(osr_entry_id));
3855 HContext* context = new(zone()) HContext; 3862 HContext* context = new(zone()) HContext;
3856 AddInstruction(context); 3863 AddInstruction(context);
3857 environment()->BindContext(context); 3864 environment()->BindContext(context);
(...skipping 607 matching lines...)
4465 expr->fast_elements(), 4472 expr->fast_elements(),
4466 expr->literal_index(), 4473 expr->literal_index(),
4467 expr->depth(), 4474 expr->depth(),
4468 expr->has_function()); 4475 expr->has_function());
4469 } 4476 }
4470 4477
4471 // The object is expected in the bailout environment during computation 4478 // The object is expected in the bailout environment during computation
4472 // of the property values and is the value of the entire expression. 4479 // of the property values and is the value of the entire expression.
4473 PushAndAdd(literal); 4480 PushAndAdd(literal);
4474 4481
4475 expr->CalculateEmitStore(); 4482 expr->CalculateEmitStore(zone());
4476 4483
4477 for (int i = 0; i < expr->properties()->length(); i++) { 4484 for (int i = 0; i < expr->properties()->length(); i++) {
4478 ObjectLiteral::Property* property = expr->properties()->at(i); 4485 ObjectLiteral::Property* property = expr->properties()->at(i);
4479 if (property->IsCompileTimeValue()) continue; 4486 if (property->IsCompileTimeValue()) continue;
4480 4487
4481 Literal* key = property->key(); 4488 Literal* key = property->key();
4482 Expression* value = property->value(); 4489 Expression* value = property->value();
4483 4490
4484 switch (property->kind()) { 4491 switch (property->kind()) {
4485 case ObjectLiteral::Property::MATERIALIZED_LITERAL: 4492 case ObjectLiteral::Property::MATERIALIZED_LITERAL:
(...skipping 169 matching lines...)
4655 4662
4656 HInstruction* HGraphBuilder::BuildStoreNamedField(HValue* object, 4663 HInstruction* HGraphBuilder::BuildStoreNamedField(HValue* object,
4657 Handle<String> name, 4664 Handle<String> name,
4658 HValue* value, 4665 HValue* value,
4659 Handle<Map> type, 4666 Handle<Map> type,
4660 LookupResult* lookup, 4667 LookupResult* lookup,
4661 bool smi_and_map_check) { 4668 bool smi_and_map_check) {
4662 ASSERT(lookup->IsFound()); 4669 ASSERT(lookup->IsFound());
4663 if (smi_and_map_check) { 4670 if (smi_and_map_check) {
4664 AddInstruction(new(zone()) HCheckNonSmi(object)); 4671 AddInstruction(new(zone()) HCheckNonSmi(object));
4665 AddInstruction(HCheckMaps::NewWithTransitions(object, type)); 4672 AddInstruction(HCheckMaps::NewWithTransitions(object, type, zone()));
4666 } 4673 }
4667 4674
4668 // If the property does not exist yet, we have to check that it wasn't made 4675 // If the property does not exist yet, we have to check that it wasn't made
4669 // readonly or turned into a setter by some meanwhile modifications on the 4676 // readonly or turned into a setter by some meanwhile modifications on the
4670 // prototype chain. 4677 // prototype chain.
4671 if (!lookup->IsProperty()) { 4678 if (!lookup->IsProperty()) {
4672 Object* proto = type->prototype(); 4679 Object* proto = type->prototype();
4673 // First check that the prototype chain isn't affected already. 4680 // First check that the prototype chain isn't affected already.
4674 LookupResult proto_result(isolate()); 4681 LookupResult proto_result(isolate());
4675 proto->Lookup(*name, &proto_result); 4682 proto->Lookup(*name, &proto_result);
(...skipping 123 matching lines...)
4799 (is_in_object == previous_field_is_in_object); 4806 (is_in_object == previous_field_is_in_object);
4800 } 4807 }
4801 ++count; 4808 ++count;
4802 } 4809 }
4803 } 4810 }
4804 4811
4805 // Use monomorphic load if property lookup results in the same field index 4812 // Use monomorphic load if property lookup results in the same field index
4806 // for all maps. Requires special map check on the set of all handled maps. 4813 // for all maps. Requires special map check on the set of all handled maps.
4807 HInstruction* instr; 4814 HInstruction* instr;
4808 if (count == types->length() && is_monomorphic_field) { 4815 if (count == types->length() && is_monomorphic_field) {
4809 AddInstruction(new(zone()) HCheckMaps(object, types)); 4816 AddInstruction(new(zone()) HCheckMaps(object, types, zone()));
4810 instr = BuildLoadNamedField(object, expr, map, &lookup, false); 4817 instr = BuildLoadNamedField(object, expr, map, &lookup, false);
4811 } else { 4818 } else {
4812 HValue* context = environment()->LookupContext(); 4819 HValue* context = environment()->LookupContext();
4813 instr = new(zone()) HLoadNamedFieldPolymorphic(context, 4820 instr = new(zone()) HLoadNamedFieldPolymorphic(context,
4814 object, 4821 object,
4815 types, 4822 types,
4816 name); 4823 name,
4824 zone());
4817 } 4825 }
4818 4826
4819 instr->set_position(expr->position()); 4827 instr->set_position(expr->position());
4820 return ast_context()->ReturnInstruction(instr, expr->id()); 4828 return ast_context()->ReturnInstruction(instr, expr->id());
4821 } 4829 }
4822 4830
4823 4831
4824 void HGraphBuilder::HandlePolymorphicStoreNamedField(Assignment* expr, 4832 void HGraphBuilder::HandlePolymorphicStoreNamedField(Assignment* expr,
4825 HValue* object, 4833 HValue* object,
4826 HValue* value, 4834 HValue* value,
(...skipping 66 matching lines...)
4893 ASSERT(join != NULL); 4901 ASSERT(join != NULL);
4894 join->SetJoinId(expr->id()); 4902 join->SetJoinId(expr->id());
4895 set_current_block(join); 4903 set_current_block(join);
4896 if (!ast_context()->IsEffect()) return ast_context()->ReturnValue(Pop()); 4904 if (!ast_context()->IsEffect()) return ast_context()->ReturnValue(Pop());
4897 } 4905 }
4898 4906
4899 4907
4900 void HGraphBuilder::HandlePropertyAssignment(Assignment* expr) { 4908 void HGraphBuilder::HandlePropertyAssignment(Assignment* expr) {
4901 Property* prop = expr->target()->AsProperty(); 4909 Property* prop = expr->target()->AsProperty();
4902 ASSERT(prop != NULL); 4910 ASSERT(prop != NULL);
4903 expr->RecordTypeFeedback(oracle()); 4911 expr->RecordTypeFeedback(oracle(), zone());
4904 CHECK_ALIVE(VisitForValue(prop->obj())); 4912 CHECK_ALIVE(VisitForValue(prop->obj()));
4905 4913
4906 HValue* value = NULL; 4914 HValue* value = NULL;
4907 HInstruction* instr = NULL; 4915 HInstruction* instr = NULL;
4908 4916
4909 if (prop->key()->IsPropertyName()) { 4917 if (prop->key()->IsPropertyName()) {
4910 // Named store. 4918 // Named store.
4911 CHECK_ALIVE(VisitForValue(expr->value())); 4919 CHECK_ALIVE(VisitForValue(expr->value()));
4912 value = Pop(); 4920 value = Pop();
4913 HValue* object = Pop(); 4921 HValue* object = Pop();
(...skipping 150 matching lines...)
5064 } 5072 }
5065 break; 5073 break;
5066 } 5074 }
5067 5075
5068 case Variable::LOOKUP: 5076 case Variable::LOOKUP:
5069 return Bailout("compound assignment to lookup slot"); 5077 return Bailout("compound assignment to lookup slot");
5070 } 5078 }
5071 return ast_context()->ReturnValue(Pop()); 5079 return ast_context()->ReturnValue(Pop());
5072 5080
5073 } else if (prop != NULL) { 5081 } else if (prop != NULL) {
5074 prop->RecordTypeFeedback(oracle()); 5082 prop->RecordTypeFeedback(oracle(), zone());
5075 5083
5076 if (prop->key()->IsPropertyName()) { 5084 if (prop->key()->IsPropertyName()) {
5077 // Named property. 5085 // Named property.
5078 CHECK_ALIVE(VisitForValue(prop->obj())); 5086 CHECK_ALIVE(VisitForValue(prop->obj()));
5079 HValue* obj = Top(); 5087 HValue* obj = Top();
5080 5088
5081 HInstruction* load = NULL; 5089 HInstruction* load = NULL;
5082 if (prop->IsMonomorphic()) { 5090 if (prop->IsMonomorphic()) {
5083 Handle<String> name = prop->key()->AsLiteral()->AsPropertyName(); 5091 Handle<String> name = prop->key()->AsLiteral()->AsPropertyName();
5084 Handle<Map> map = prop->GetReceiverTypes()->first(); 5092 Handle<Map> map = prop->GetReceiverTypes()->first();
(...skipping 38 matching lines...)
5123 5131
5124 5132
5125 CHECK_ALIVE(VisitForValue(expr->value())); 5133 CHECK_ALIVE(VisitForValue(expr->value()));
5126 HValue* right = Pop(); 5134 HValue* right = Pop();
5127 HValue* left = Pop(); 5135 HValue* left = Pop();
5128 5136
5129 HInstruction* instr = BuildBinaryOperation(operation, left, right); 5137 HInstruction* instr = BuildBinaryOperation(operation, left, right);
5130 PushAndAdd(instr); 5138 PushAndAdd(instr);
5131 if (instr->HasObservableSideEffects()) AddSimulate(operation->id()); 5139 if (instr->HasObservableSideEffects()) AddSimulate(operation->id());
5132 5140
5133 expr->RecordTypeFeedback(oracle()); 5141 expr->RecordTypeFeedback(oracle(), zone());
5134 HandleKeyedElementAccess(obj, key, instr, expr, expr->AssignmentId(), 5142 HandleKeyedElementAccess(obj, key, instr, expr, expr->AssignmentId(),
5135 RelocInfo::kNoPosition, 5143 RelocInfo::kNoPosition,
5136 true, // is_store 5144 true, // is_store
5137 &has_side_effects); 5145 &has_side_effects);
5138 5146
5139 // Drop the simulated receiver, key, and value. Return the value. 5147 // Drop the simulated receiver, key, and value. Return the value.
5140 Drop(3); 5148 Drop(3);
5141 Push(instr); 5149 Push(instr);
5142 ASSERT(has_side_effects); // Stores always have side effects. 5150 ASSERT(has_side_effects); // Stores always have side effects.
5143 AddSimulate(expr->AssignmentId()); 5151 AddSimulate(expr->AssignmentId());
(...skipping 27 matching lines...)
5171 if (var->mode() == CONST) { 5179 if (var->mode() == CONST) {
5172 if (expr->op() != Token::INIT_CONST) { 5180 if (expr->op() != Token::INIT_CONST) {
5173 CHECK_ALIVE(VisitForValue(expr->value())); 5181 CHECK_ALIVE(VisitForValue(expr->value()));
5174 return ast_context()->ReturnValue(Pop()); 5182 return ast_context()->ReturnValue(Pop());
5175 } 5183 }
5176 5184
5177 if (var->IsStackAllocated()) { 5185 if (var->IsStackAllocated()) {
5178 // We insert a use of the old value to detect unsupported uses of const 5186 // We insert a use of the old value to detect unsupported uses of const
5179 // variables (e.g. initialization inside a loop). 5187 // variables (e.g. initialization inside a loop).
5180 HValue* old_value = environment()->Lookup(var); 5188 HValue* old_value = environment()->Lookup(var);
5181 AddInstruction(new HUseConst(old_value)); 5189 AddInstruction(new(zone()) HUseConst(old_value));
5182 } 5190 }
5183 } else if (var->mode() == CONST_HARMONY) { 5191 } else if (var->mode() == CONST_HARMONY) {
5184 if (expr->op() != Token::INIT_CONST_HARMONY) { 5192 if (expr->op() != Token::INIT_CONST_HARMONY) {
5185 return Bailout("non-initializer assignment to const"); 5193 return Bailout("non-initializer assignment to const");
5186 } 5194 }
5187 } 5195 }
5188 5196
5189 if (proxy->IsArguments()) return Bailout("assignment to arguments"); 5197 if (proxy->IsArguments()) return Bailout("assignment to arguments");
5190 5198
5191 // Handle the assignment. 5199 // Handle the assignment.
(...skipping 106 matching lines...)
5298 } 5306 }
5299 5307
5300 5308
5301 HLoadNamedField* HGraphBuilder::BuildLoadNamedField(HValue* object, 5309 HLoadNamedField* HGraphBuilder::BuildLoadNamedField(HValue* object,
5302 Property* expr, 5310 Property* expr,
5303 Handle<Map> type, 5311 Handle<Map> type,
5304 LookupResult* lookup, 5312 LookupResult* lookup,
5305 bool smi_and_map_check) { 5313 bool smi_and_map_check) {
5306 if (smi_and_map_check) { 5314 if (smi_and_map_check) {
5307 AddInstruction(new(zone()) HCheckNonSmi(object)); 5315 AddInstruction(new(zone()) HCheckNonSmi(object));
5308 AddInstruction(HCheckMaps::NewWithTransitions(object, type)); 5316 AddInstruction(HCheckMaps::NewWithTransitions(object, type, zone()));
5309 } 5317 }
5310 5318
5311 int index = lookup->GetLocalFieldIndexFromMap(*type); 5319 int index = lookup->GetLocalFieldIndexFromMap(*type);
5312 if (index < 0) { 5320 if (index < 0) {
5313 // Negative property indices are in-object properties, indexed 5321 // Negative property indices are in-object properties, indexed
5314 // from the end of the fixed part of the object. 5322 // from the end of the fixed part of the object.
5315 int offset = (index * kPointerSize) + type->instance_size(); 5323 int offset = (index * kPointerSize) + type->instance_size();
5316 return new(zone()) HLoadNamedField(object, true, offset); 5324 return new(zone()) HLoadNamedField(object, true, offset);
5317 } else { 5325 } else {
5318 // Non-negative property indices are in the properties array. 5326 // Non-negative property indices are in the properties array.
(...skipping 23 matching lines...)
5342 LookupResult lookup(isolate()); 5350 LookupResult lookup(isolate());
5343 map->LookupInDescriptors(NULL, *name, &lookup); 5351 map->LookupInDescriptors(NULL, *name, &lookup);
5344 if (lookup.IsFound() && lookup.type() == FIELD) { 5352 if (lookup.IsFound() && lookup.type() == FIELD) {
5345 return BuildLoadNamedField(obj, 5353 return BuildLoadNamedField(obj,
5346 expr, 5354 expr,
5347 map, 5355 map,
5348 &lookup, 5356 &lookup,
5349 true); 5357 true);
5350 } else if (lookup.IsFound() && lookup.type() == CONSTANT_FUNCTION) { 5358 } else if (lookup.IsFound() && lookup.type() == CONSTANT_FUNCTION) {
5351 AddInstruction(new(zone()) HCheckNonSmi(obj)); 5359 AddInstruction(new(zone()) HCheckNonSmi(obj));
5352 AddInstruction(HCheckMaps::NewWithTransitions(obj, map)); 5360 AddInstruction(HCheckMaps::NewWithTransitions(obj, map, zone()));
5353 Handle<JSFunction> function(lookup.GetConstantFunctionFromMap(*map)); 5361 Handle<JSFunction> function(lookup.GetConstantFunctionFromMap(*map));
5354 return new(zone()) HConstant(function, Representation::Tagged()); 5362 return new(zone()) HConstant(function, Representation::Tagged());
5355 } else { 5363 } else {
5356 return BuildLoadNamedGeneric(obj, expr); 5364 return BuildLoadNamedGeneric(obj, expr);
5357 } 5365 }
5358 } 5366 }
5359 5367
5360 5368
5361 HInstruction* HGraphBuilder::BuildLoadKeyedGeneric(HValue* object, 5369 HInstruction* HGraphBuilder::BuildLoadKeyedGeneric(HValue* object,
5362 HValue* key) { 5370 HValue* key) {
(...skipping 92 matching lines...)
5455 } 5463 }
5456 5464
5457 5465
5458 HInstruction* HGraphBuilder::BuildMonomorphicElementAccess(HValue* object, 5466 HInstruction* HGraphBuilder::BuildMonomorphicElementAccess(HValue* object,
5459 HValue* key, 5467 HValue* key,
5460 HValue* val, 5468 HValue* val,
5461 HValue* dependency, 5469 HValue* dependency,
5462 Handle<Map> map, 5470 Handle<Map> map,
5463 bool is_store) { 5471 bool is_store) {
5464 HInstruction* mapcheck = 5472 HInstruction* mapcheck =
5465 AddInstruction(new(zone()) HCheckMaps(object, map, dependency)); 5473 AddInstruction(new(zone()) HCheckMaps(object, map, zone(), dependency));
5466 // No GVNFlag is necessary for ElementsKind if there is an explicit dependency 5474 // No GVNFlag is necessary for ElementsKind if there is an explicit dependency
5467 // on a HElementsTransition instruction. The flag can also be removed if the 5475 // on a HElementsTransition instruction. The flag can also be removed if the
5468 // map to check has FAST_HOLEY_ELEMENTS, since there can be no further 5476 // map to check has FAST_HOLEY_ELEMENTS, since there can be no further
5469 // ElementsKind transitions. Finally, the dependency can be removed for stores 5477 // ElementsKind transitions. Finally, the dependency can be removed for stores
5470 // for FAST_ELEMENTS, since a transition to HOLEY elements won't change the 5478 // for FAST_ELEMENTS, since a transition to HOLEY elements won't change the
5471 // generated store code. 5479 // generated store code.
5472 if (dependency || 5480 if (dependency ||
5473 (map->elements_kind() == FAST_HOLEY_ELEMENTS) || 5481 (map->elements_kind() == FAST_HOLEY_ELEMENTS) ||
5474 (map->elements_kind() == FAST_ELEMENTS && is_store)) { 5482 (map->elements_kind() == FAST_ELEMENTS && is_store)) {
5475 mapcheck->ClearGVNFlag(kDependsOnElementsKind); 5483 mapcheck->ClearGVNFlag(kDependsOnElementsKind);
5476 } 5484 }
5477 bool fast_smi_only_elements = map->has_fast_smi_elements(); 5485 bool fast_smi_only_elements = map->has_fast_smi_elements();
5478 bool fast_elements = map->has_fast_object_elements(); 5486 bool fast_elements = map->has_fast_object_elements();
5479 HInstruction* elements = AddInstruction(new(zone()) HLoadElements(object)); 5487 HInstruction* elements = AddInstruction(new(zone()) HLoadElements(object));
5480 if (is_store && (fast_elements || fast_smi_only_elements)) { 5488 if (is_store && (fast_elements || fast_smi_only_elements)) {
5481 HCheckMaps* check_cow_map = new(zone()) HCheckMaps( 5489 HCheckMaps* check_cow_map = new(zone()) HCheckMaps(
5482 elements, isolate()->factory()->fixed_array_map()); 5490 elements, isolate()->factory()->fixed_array_map(), zone());
5483 check_cow_map->ClearGVNFlag(kDependsOnElementsKind); 5491 check_cow_map->ClearGVNFlag(kDependsOnElementsKind);
5484 AddInstruction(check_cow_map); 5492 AddInstruction(check_cow_map);
5485 } 5493 }
5486 HInstruction* length = NULL; 5494 HInstruction* length = NULL;
5487 HInstruction* checked_key = NULL; 5495 HInstruction* checked_key = NULL;
5488 if (map->has_external_array_elements()) { 5496 if (map->has_external_array_elements()) {
5489 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements)); 5497 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements));
5490 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length)); 5498 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length));
5491 HLoadExternalArrayPointer* external_elements = 5499 HLoadExternalArrayPointer* external_elements =
5492 new(zone()) HLoadExternalArrayPointer(elements); 5500 new(zone()) HLoadExternalArrayPointer(elements);
(...skipping 86 matching lines...)
5579 : BuildLoadKeyedGeneric(object, key)); 5587 : BuildLoadKeyedGeneric(object, key));
5580 } else { 5588 } else {
5581 instr = AddInstruction(BuildMonomorphicElementAccess( 5589 instr = AddInstruction(BuildMonomorphicElementAccess(
5582 object, key, val, transition, untransitionable_map, is_store)); 5590 object, key, val, transition, untransitionable_map, is_store));
5583 } 5591 }
5584 *has_side_effects |= instr->HasObservableSideEffects(); 5592 *has_side_effects |= instr->HasObservableSideEffects();
5585 instr->set_position(position); 5593 instr->set_position(position);
5586 return is_store ? NULL : instr; 5594 return is_store ? NULL : instr;
5587 } 5595 }
5588 5596
5589 AddInstruction(HCheckInstanceType::NewIsSpecObject(object)); 5597 AddInstruction(HCheckInstanceType::NewIsSpecObject(object, graph()->zone()));
danno 2012/06/05 13:42:35 use just zone()
sanjoy 2012/06/05 14:21:39 Fixed.
5590 HBasicBlock* join = graph()->CreateBasicBlock(); 5598 HBasicBlock* join = graph()->CreateBasicBlock();
5591 5599
5592 HInstruction* elements_kind_instr = 5600 HInstruction* elements_kind_instr =
5593 AddInstruction(new(zone()) HElementsKind(object)); 5601 AddInstruction(new(zone()) HElementsKind(object));
5594 HCompareConstantEqAndBranch* elements_kind_branch = NULL; 5602 HCompareConstantEqAndBranch* elements_kind_branch = NULL;
5595 HInstruction* elements = AddInstruction(new(zone()) HLoadElements(object)); 5603 HInstruction* elements = AddInstruction(new(zone()) HLoadElements(object));
5596 HLoadExternalArrayPointer* external_elements = NULL; 5604 HLoadExternalArrayPointer* external_elements = NULL;
5597 HInstruction* checked_key = NULL; 5605 HInstruction* checked_key = NULL;
5598 5606
5599 // Generated code assumes that FAST_* and DICTIONARY_ELEMENTS ElementsKinds 5607 // Generated code assumes that FAST_* and DICTIONARY_ELEMENTS ElementsKinds
(...skipping 26 matching lines...)
5626 elements_kind_branch->SetSuccessorAt(0, if_true); 5634 elements_kind_branch->SetSuccessorAt(0, if_true);
5627 elements_kind_branch->SetSuccessorAt(1, if_false); 5635 elements_kind_branch->SetSuccessorAt(1, if_false);
5628 current_block()->Finish(elements_kind_branch); 5636 current_block()->Finish(elements_kind_branch);
5629 5637
5630 set_current_block(if_true); 5638 set_current_block(if_true);
5631 HInstruction* access; 5639 HInstruction* access;
5632 if (IsFastElementsKind(elements_kind)) { 5640 if (IsFastElementsKind(elements_kind)) {
5633 if (is_store && !IsFastDoubleElementsKind(elements_kind)) { 5641 if (is_store && !IsFastDoubleElementsKind(elements_kind)) {
5634 AddInstruction(new(zone()) HCheckMaps( 5642 AddInstruction(new(zone()) HCheckMaps(
5635 elements, isolate()->factory()->fixed_array_map(), 5643 elements, isolate()->factory()->fixed_array_map(),
5636 elements_kind_branch)); 5644 zone(), elements_kind_branch));
5637 } 5645 }
5638 // TODO(jkummerow): The need for these two blocks could be avoided 5646 // TODO(jkummerow): The need for these two blocks could be avoided
5639 // in one of two ways: 5647 // in one of two ways:
5640 // (1) Introduce ElementsKinds for JSArrays that are distinct from 5648 // (1) Introduce ElementsKinds for JSArrays that are distinct from
5641 // those for fast objects. 5649 // those for fast objects.
5642 // (2) Put the common instructions into a third "join" block. This 5650 // (2) Put the common instructions into a third "join" block. This
5643 // requires additional AST IDs that we can deopt to from inside 5651 // requires additional AST IDs that we can deopt to from inside
5644 // that join block. They must be added to the Property class (when 5652 // that join block. They must be added to the Property class (when
5645 // it's a keyed property) and registered in the full codegen. 5653 // it's a keyed property) and registered in the full codegen.
5646 HBasicBlock* if_jsarray = graph()->CreateBasicBlock(); 5654 HBasicBlock* if_jsarray = graph()->CreateBasicBlock();
(...skipping 186 matching lines...)
5833 } 5841 }
5834 ast_context()->ReturnInstruction(result, expr->id()); 5842 ast_context()->ReturnInstruction(result, expr->id());
5835 return true; 5843 return true;
5836 } 5844 }
5837 5845
5838 5846
5839 void HGraphBuilder::VisitProperty(Property* expr) { 5847 void HGraphBuilder::VisitProperty(Property* expr) {
5840 ASSERT(!HasStackOverflow()); 5848 ASSERT(!HasStackOverflow());
5841 ASSERT(current_block() != NULL); 5849 ASSERT(current_block() != NULL);
5842 ASSERT(current_block()->HasPredecessor()); 5850 ASSERT(current_block()->HasPredecessor());
5843 expr->RecordTypeFeedback(oracle()); 5851 expr->RecordTypeFeedback(oracle(), zone());
5844 5852
5845 if (TryArgumentsAccess(expr)) return; 5853 if (TryArgumentsAccess(expr)) return;
5846 5854
5847 CHECK_ALIVE(VisitForValue(expr->obj())); 5855 CHECK_ALIVE(VisitForValue(expr->obj()));
5848 5856
5849 HInstruction* instr = NULL; 5857 HInstruction* instr = NULL;
5850 if (expr->AsProperty()->IsArrayLength()) { 5858 if (expr->AsProperty()->IsArrayLength()) {
5851 HValue* array = Pop(); 5859 HValue* array = Pop();
5852 AddInstruction(new(zone()) HCheckNonSmi(array)); 5860 AddInstruction(new(zone()) HCheckNonSmi(array));
5853 HInstruction* mapcheck = 5861 HInstruction* mapcheck =
5854 AddInstruction(HCheckInstanceType::NewIsJSArray(array)); 5862 AddInstruction(HCheckInstanceType::NewIsJSArray(array, zone()));
5855 instr = new(zone()) HJSArrayLength(array, mapcheck); 5863 instr = new(zone()) HJSArrayLength(array, mapcheck);
5856 5864
5857 } else if (expr->IsStringLength()) { 5865 } else if (expr->IsStringLength()) {
5858 HValue* string = Pop(); 5866 HValue* string = Pop();
5859 AddInstruction(new(zone()) HCheckNonSmi(string)); 5867 AddInstruction(new(zone()) HCheckNonSmi(string));
5860 AddInstruction(HCheckInstanceType::NewIsString(string)); 5868 AddInstruction(HCheckInstanceType::NewIsString(string, zone()));
5861 instr = new(zone()) HStringLength(string); 5869 instr = new(zone()) HStringLength(string);
5862 } else if (expr->IsStringAccess()) { 5870 } else if (expr->IsStringAccess()) {
5863 CHECK_ALIVE(VisitForValue(expr->key())); 5871 CHECK_ALIVE(VisitForValue(expr->key()));
5864 HValue* index = Pop(); 5872 HValue* index = Pop();
5865 HValue* string = Pop(); 5873 HValue* string = Pop();
5866 HValue* context = environment()->LookupContext(); 5874 HValue* context = environment()->LookupContext();
5867 HStringCharCodeAt* char_code = 5875 HStringCharCodeAt* char_code =
5868 BuildStringCharCodeAt(context, string, index); 5876 BuildStringCharCodeAt(context, string, index);
5869 AddInstruction(char_code); 5877 AddInstruction(char_code);
5870 instr = new(zone()) HStringCharFromCode(context, char_code); 5878 instr = new(zone()) HStringCharFromCode(context, char_code);
(...skipping 47 matching lines...)
5918 5926
5919 void HGraphBuilder::AddCheckConstantFunction(Call* expr, 5927 void HGraphBuilder::AddCheckConstantFunction(Call* expr,
5920 HValue* receiver, 5928 HValue* receiver,
5921 Handle<Map> receiver_map, 5929 Handle<Map> receiver_map,
5922 bool smi_and_map_check) { 5930 bool smi_and_map_check) {
5923 // Constant functions have the nice property that the map will change if they 5931 // Constant functions have the nice property that the map will change if they
5924 // are overwritten. Therefore it is enough to check the map of the holder and 5932 // are overwritten. Therefore it is enough to check the map of the holder and
5925 // its prototypes. 5933 // its prototypes.
5926 if (smi_and_map_check) { 5934 if (smi_and_map_check) {
5927 AddInstruction(new(zone()) HCheckNonSmi(receiver)); 5935 AddInstruction(new(zone()) HCheckNonSmi(receiver));
5928 AddInstruction(HCheckMaps::NewWithTransitions(receiver, receiver_map)); 5936 AddInstruction(HCheckMaps::NewWithTransitions(receiver, receiver_map,
5937 zone()));
5929 } 5938 }
5930 if (!expr->holder().is_null()) { 5939 if (!expr->holder().is_null()) {
5931 AddInstruction(new(zone()) HCheckPrototypeMaps( 5940 AddInstruction(new(zone()) HCheckPrototypeMaps(
5932 Handle<JSObject>(JSObject::cast(receiver_map->prototype())), 5941 Handle<JSObject>(JSObject::cast(receiver_map->prototype())),
5933 expr->holder())); 5942 expr->holder()));
5934 } 5943 }
5935 } 5944 }
5936 5945
5937 5946
5938 class FunctionSorter { 5947 class FunctionSorter {
(...skipping 314 matching lines...)
6253 // generating the optimized inline code. 6262 // generating the optimized inline code.
6254 target_info.EnableDeoptimizationSupport(); 6263 target_info.EnableDeoptimizationSupport();
6255 if (!FullCodeGenerator::MakeCode(&target_info)) { 6264 if (!FullCodeGenerator::MakeCode(&target_info)) {
6256 TraceInline(target, caller, "could not generate deoptimization info"); 6265 TraceInline(target, caller, "could not generate deoptimization info");
6257 return false; 6266 return false;
6258 } 6267 }
6259 if (target_shared->scope_info() == ScopeInfo::Empty()) { 6268 if (target_shared->scope_info() == ScopeInfo::Empty()) {
6260 // The scope info might not have been set if a lazily compiled 6269 // The scope info might not have been set if a lazily compiled
6261 // function is inlined before being called for the first time. 6270 // function is inlined before being called for the first time.
6262 Handle<ScopeInfo> target_scope_info = 6271 Handle<ScopeInfo> target_scope_info =
6263 ScopeInfo::Create(target_info.scope()); 6272 ScopeInfo::Create(target_info.scope(), zone());
6264 target_shared->set_scope_info(*target_scope_info); 6273 target_shared->set_scope_info(*target_scope_info);
6265 } 6274 }
6266 target_shared->EnableDeoptimizationSupport(*target_info.code()); 6275 target_shared->EnableDeoptimizationSupport(*target_info.code());
6267 Compiler::RecordFunctionCompilation(Logger::FUNCTION_TAG, 6276 Compiler::RecordFunctionCompilation(Logger::FUNCTION_TAG,
6268 &target_info, 6277 &target_info,
6269 target_shared); 6278 target_shared);
6270 } 6279 }
6271 6280
6272 // ---------------------------------------------------------------- 6281 // ----------------------------------------------------------------
6273 // After this point, we've made a decision to inline this function (so 6282 // After this point, we've made a decision to inline this function (so
6274 // TryInline should always return true). 6283 // TryInline should always return true).
6275 6284
6276 // Save the pending call context and type feedback oracle. Set up new ones 6285 // Save the pending call context and type feedback oracle. Set up new ones
6277 // for the inlined function. 6286 // for the inlined function.
6278 ASSERT(target_shared->has_deoptimization_support()); 6287 ASSERT(target_shared->has_deoptimization_support());
6279 TypeFeedbackOracle target_oracle( 6288 TypeFeedbackOracle target_oracle(
6280 Handle<Code>(target_shared->code()), 6289 Handle<Code>(target_shared->code()),
6281 Handle<Context>(target->context()->global_context()), 6290 Handle<Context>(target->context()->global_context()),
6282 isolate()); 6291 isolate(),
6292 zone());
6283 // The function state is new-allocated because we need to delete it 6293 // The function state is new-allocated because we need to delete it
6284 // in two different places. 6294 // in two different places.
6285 FunctionState* target_state = new FunctionState( 6295 FunctionState* target_state = new FunctionState(
6286 this, &target_info, &target_oracle, return_handling); 6296 this, &target_info, &target_oracle, return_handling);
6287 6297
6288 HConstant* undefined = graph()->GetConstantUndefined(); 6298 HConstant* undefined = graph()->GetConstantUndefined();
6289 HEnvironment* inner_env = 6299 HEnvironment* inner_env =
6290 environment()->CopyForInlining(target, 6300 environment()->CopyForInlining(target,
6291 arguments->length(), 6301 arguments->length(),
6292 function, 6302 function,
6293 undefined, 6303 undefined,
6294 call_kind, 6304 call_kind,
6295 function_state()->is_construct()); 6305 function_state()->is_construct());
6296 #ifdef V8_TARGET_ARCH_IA32 6306 #ifdef V8_TARGET_ARCH_IA32
6297 // IA32 only, overwrite the caller's context in the deoptimization 6307 // IA32 only, overwrite the caller's context in the deoptimization
6298 // environment with the correct one. 6308 // environment with the correct one.
6299 // 6309 //
6300 // TODO(kmillikin): implement the same inlining on other platforms so we 6310 // TODO(kmillikin): implement the same inlining on other platforms so we
6301 // can remove the unsightly ifdefs in this function. 6311 // can remove the unsightly ifdefs in this function.
6302 HConstant* context = new HConstant(Handle<Context>(target->context()), 6312 HConstant* context =
6303 Representation::Tagged()); 6313 new(isolate()->zone()) HConstant(Handle<Context>(target->context()),
danno 2012/06/05 13:42:35 why not just zone()?
sanjoy 2012/06/05 14:21:39 Fixed.
6314 Representation::Tagged());
6304 AddInstruction(context); 6315 AddInstruction(context);
6305 inner_env->BindContext(context); 6316 inner_env->BindContext(context);
6306 #endif 6317 #endif
6307 6318
6308 AddSimulate(return_id); 6319 AddSimulate(return_id);
6309 current_block()->UpdateEnvironment(inner_env); 6320 current_block()->UpdateEnvironment(inner_env);
6310 6321
6311 ZoneList<HValue*>* arguments_values = NULL; 6322 ZoneList<HValue*>* arguments_values = NULL;
6312 6323
6313 // If the function uses arguments copy current arguments values 6324 // If the function uses arguments copy current arguments values
6314 // to use them for materialization. 6325 // to use them for materialization.
6315 if (function->scope()->arguments() != NULL) { 6326 if (function->scope()->arguments() != NULL) {
6316 HEnvironment* arguments_env = inner_env->arguments_environment(); 6327 HEnvironment* arguments_env = inner_env->arguments_environment();
6317 int arguments_count = arguments_env->parameter_count(); 6328 int arguments_count = arguments_env->parameter_count();
6318 arguments_values = new(zone()) ZoneList<HValue*>(arguments_count); 6329 arguments_values = new(zone()) ZoneList<HValue*>(arguments_count, zone());
6319 for (int i = 0; i < arguments_count; i++) { 6330 for (int i = 0; i < arguments_count; i++) {
6320 arguments_values->Add(arguments_env->Lookup(i)); 6331 arguments_values->Add(arguments_env->Lookup(i), zone());
6321 } 6332 }
6322 } 6333 }
6323 6334
6324 HEnterInlined* enter_inlined = 6335 HEnterInlined* enter_inlined =
6325 new(zone()) HEnterInlined(target, 6336 new(zone()) HEnterInlined(target,
6326 arguments->length(), 6337 arguments->length(),
6327 function, 6338 function,
6328 call_kind, 6339 call_kind,
6329 function_state()->is_construct(), 6340 function_state()->is_construct(),
6330 function->scope()->arguments(), 6341 function->scope()->arguments(),
(...skipping 574 matching lines...)
6905 Drop(argument_count); 6916 Drop(argument_count);
6906 } 6917 }
6907 6918
6908 } else if (expr->IsMonomorphic()) { 6919 } else if (expr->IsMonomorphic()) {
6909 // The function is on the stack in the unoptimized code during 6920 // The function is on the stack in the unoptimized code during
6910 // evaluation of the arguments. 6921 // evaluation of the arguments.
6911 CHECK_ALIVE(VisitForValue(expr->expression())); 6922 CHECK_ALIVE(VisitForValue(expr->expression()));
6912 HValue* function = Top(); 6923 HValue* function = Top();
6913 HValue* context = environment()->LookupContext(); 6924 HValue* context = environment()->LookupContext();
6914 HGlobalObject* global = new(zone()) HGlobalObject(context); 6925 HGlobalObject* global = new(zone()) HGlobalObject(context);
6926 AddInstruction(global);
sanjoy 2012/06/05 13:02:49 This needs to be done so that the HGlobalReceiver
6915 HGlobalReceiver* receiver = new(zone()) HGlobalReceiver(global); 6927 HGlobalReceiver* receiver = new(zone()) HGlobalReceiver(global);
6916 AddInstruction(global);
6917 PushAndAdd(receiver); 6928 PushAndAdd(receiver);
6918 CHECK_ALIVE(VisitExpressions(expr->arguments())); 6929 CHECK_ALIVE(VisitExpressions(expr->arguments()));
6919 AddInstruction(new(zone()) HCheckFunction(function, expr->target())); 6930 AddInstruction(new(zone()) HCheckFunction(function, expr->target()));
6920 6931
6921 if (TryInlineBuiltinFunctionCall(expr, true)) { // Drop the function. 6932 if (TryInlineBuiltinFunctionCall(expr, true)) { // Drop the function.
6922 if (FLAG_trace_inlining) { 6933 if (FLAG_trace_inlining) {
6923 PrintF("Inlining builtin "); 6934 PrintF("Inlining builtin ");
6924 expr->target()->ShortPrint(); 6935 expr->target()->ShortPrint();
6925 PrintF("\n"); 6936 PrintF("\n");
6926 } 6937 }
6927 return; 6938 return;
6928 } 6939 }
6929 6940
6930 if (TryInlineCall(expr, true)) { // Drop function from environment. 6941 if (TryInlineCall(expr, true)) { // Drop function from environment.
6931 return; 6942 return;
6932 } else { 6943 } else {
6933 call = PreProcessCall( 6944 call = PreProcessCall(
6934 new(zone()) HInvokeFunction(context, 6945 new(zone()) HInvokeFunction(context,
6935 function, 6946 function,
6936 expr->target(), 6947 expr->target(),
6937 argument_count)); 6948 argument_count));
6938 Drop(1); // The function. 6949 Drop(1); // The function.
6939 } 6950 }
6940 6951
6941 } else { 6952 } else {
6942 CHECK_ALIVE(VisitForValue(expr->expression())); 6953 CHECK_ALIVE(VisitForValue(expr->expression()));
6943 HValue* function = Top(); 6954 HValue* function = Top();
6944 HValue* context = environment()->LookupContext(); 6955 HValue* context = environment()->LookupContext();
6945 HGlobalObject* global_object = new(zone()) HGlobalObject(context); 6956 HGlobalObject* global_object = new(zone()) HGlobalObject(context);
6957 AddInstruction(global_object);
6946 HGlobalReceiver* receiver = new(zone()) HGlobalReceiver(global_object); 6958 HGlobalReceiver* receiver = new(zone()) HGlobalReceiver(global_object);
6947 AddInstruction(global_object);
6948 AddInstruction(receiver); 6959 AddInstruction(receiver);
6949 PushAndAdd(new(zone()) HPushArgument(receiver)); 6960 PushAndAdd(new(zone()) HPushArgument(receiver));
6950 CHECK_ALIVE(VisitArgumentList(expr->arguments())); 6961 CHECK_ALIVE(VisitArgumentList(expr->arguments()));
6951 6962
6952 call = new(zone()) HCallFunction(context, function, argument_count); 6963 call = new(zone()) HCallFunction(context, function, argument_count);
6953 Drop(argument_count + 1); 6964 Drop(argument_count + 1);
6954 } 6965 }
6955 } 6966 }
6956 6967
6957 call->set_position(expr->position()); 6968 call->set_position(expr->position());
(...skipping 385 matching lines...)
7343 break; 7354 break;
7344 } 7355 }
7345 7356
7346 case Variable::LOOKUP: 7357 case Variable::LOOKUP:
7347 return Bailout("lookup variable in count operation"); 7358 return Bailout("lookup variable in count operation");
7348 } 7359 }
7349 7360
7350 } else { 7361 } else {
7351 // Argument of the count operation is a property. 7362 // Argument of the count operation is a property.
7352 ASSERT(prop != NULL); 7363 ASSERT(prop != NULL);
7353 prop->RecordTypeFeedback(oracle()); 7364 prop->RecordTypeFeedback(oracle(), zone());
7354 7365
7355 if (prop->key()->IsPropertyName()) { 7366 if (prop->key()->IsPropertyName()) {
7356 // Named property. 7367 // Named property.
7357 if (returns_original_input) Push(graph_->GetConstantUndefined()); 7368 if (returns_original_input) Push(graph_->GetConstantUndefined());
7358 7369
7359 CHECK_ALIVE(VisitForValue(prop->obj())); 7370 CHECK_ALIVE(VisitForValue(prop->obj()));
7360 HValue* obj = Top(); 7371 HValue* obj = Top();
7361 7372
7362 HInstruction* load = NULL; 7373 HInstruction* load = NULL;
7363 if (prop->IsMonomorphic()) { 7374 if (prop->IsMonomorphic()) {
(...skipping 33 matching lines...)
7397 HValue* load = HandleKeyedElementAccess( 7408 HValue* load = HandleKeyedElementAccess(
7398 obj, key, NULL, prop, expr->CountId(), RelocInfo::kNoPosition, 7409 obj, key, NULL, prop, expr->CountId(), RelocInfo::kNoPosition,
7399 false, // is_store 7410 false, // is_store
7400 &has_side_effects); 7411 &has_side_effects);
7401 Push(load); 7412 Push(load);
7402 if (has_side_effects) AddSimulate(expr->CountId()); 7413 if (has_side_effects) AddSimulate(expr->CountId());
7403 7414
7404 after = BuildIncrement(returns_original_input, expr); 7415 after = BuildIncrement(returns_original_input, expr);
7405 input = Pop(); 7416 input = Pop();
7406 7417
7407 expr->RecordTypeFeedback(oracle()); 7418 expr->RecordTypeFeedback(oracle(), zone());
7408 HandleKeyedElementAccess(obj, key, after, expr, expr->AssignmentId(), 7419 HandleKeyedElementAccess(obj, key, after, expr, expr->AssignmentId(),
7409 RelocInfo::kNoPosition, 7420 RelocInfo::kNoPosition,
7410 true, // is_store 7421 true, // is_store
7411 &has_side_effects); 7422 &has_side_effects);
7412 7423
7413 // Drop the key from the bailout environment. Overwrite the receiver 7424 // Drop the key from the bailout environment. Overwrite the receiver
7414 // with the result of the operation, and the placeholder with the 7425 // with the result of the operation, and the placeholder with the
7415 // original value if necessary. 7426 // original value if necessary.
7416 Drop(1); 7427 Drop(1);
7417 environment()->SetExpressionStackAt(0, after); 7428 environment()->SetExpressionStackAt(0, after);
7418 if (returns_original_input) environment()->SetExpressionStackAt(1, input); 7429 if (returns_original_input) environment()->SetExpressionStackAt(1, input);
7419 ASSERT(has_side_effects); // Stores always have side effects. 7430 ASSERT(has_side_effects); // Stores always have side effects.
7420 AddSimulate(expr->AssignmentId()); 7431 AddSimulate(expr->AssignmentId());
7421 } 7432 }
7422 } 7433 }
7423 7434
7424 Drop(returns_original_input ? 2 : 1); 7435 Drop(returns_original_input ? 2 : 1);
7425 return ast_context()->ReturnValue(expr->is_postfix() ? input : after); 7436 return ast_context()->ReturnValue(expr->is_postfix() ? input : after);
7426 } 7437 }
7427 7438
7428 7439
7429 HStringCharCodeAt* HGraphBuilder::BuildStringCharCodeAt(HValue* context, 7440 HStringCharCodeAt* HGraphBuilder::BuildStringCharCodeAt(HValue* context,
7430 HValue* string, 7441 HValue* string,
7431 HValue* index) { 7442 HValue* index) {
7432 AddInstruction(new(zone()) HCheckNonSmi(string)); 7443 AddInstruction(new(zone()) HCheckNonSmi(string));
7433 AddInstruction(HCheckInstanceType::NewIsString(string)); 7444 AddInstruction(HCheckInstanceType::NewIsString(string, zone()));
7434 HStringLength* length = new(zone()) HStringLength(string); 7445 HStringLength* length = new(zone()) HStringLength(string);
7435 AddInstruction(length); 7446 AddInstruction(length);
7436 HInstruction* checked_index = 7447 HInstruction* checked_index =
7437 AddInstruction(new(zone()) HBoundsCheck(index, length)); 7448 AddInstruction(new(zone()) HBoundsCheck(index, length));
7438 return new(zone()) HStringCharCodeAt(context, string, checked_index); 7449 return new(zone()) HStringCharCodeAt(context, string, checked_index);
7439 } 7450 }
7440 7451
7441 7452
7442 HInstruction* HGraphBuilder::BuildBinaryOperation(BinaryOperation* expr, 7453 HInstruction* HGraphBuilder::BuildBinaryOperation(BinaryOperation* expr,
7443 HValue* left, 7454 HValue* left,
7444 HValue* right) { 7455 HValue* right) {
7445 HValue* context = environment()->LookupContext(); 7456 HValue* context = environment()->LookupContext();
7446 TypeInfo info = oracle()->BinaryType(expr); 7457 TypeInfo info = oracle()->BinaryType(expr);
7447 if (info.IsUninitialized()) { 7458 if (info.IsUninitialized()) {
7448 AddInstruction(new(zone()) HSoftDeoptimize); 7459 AddInstruction(new(zone()) HSoftDeoptimize);
7449 current_block()->MarkAsDeoptimizing(); 7460 current_block()->MarkAsDeoptimizing();
7450 info = TypeInfo::Unknown(); 7461 info = TypeInfo::Unknown();
7451 } 7462 }
7452 HInstruction* instr = NULL; 7463 HInstruction* instr = NULL;
7453 switch (expr->op()) { 7464 switch (expr->op()) {
7454 case Token::ADD: 7465 case Token::ADD:
7455 if (info.IsString()) { 7466 if (info.IsString()) {
7456 AddInstruction(new(zone()) HCheckNonSmi(left)); 7467 AddInstruction(new(zone()) HCheckNonSmi(left));
7457 AddInstruction(HCheckInstanceType::NewIsString(left)); 7468 AddInstruction(HCheckInstanceType::NewIsString(left, zone()));
7458 AddInstruction(new(zone()) HCheckNonSmi(right)); 7469 AddInstruction(new(zone()) HCheckNonSmi(right));
7459 AddInstruction(HCheckInstanceType::NewIsString(right)); 7470 AddInstruction(HCheckInstanceType::NewIsString(right, zone()));
7460 instr = new(zone()) HStringAdd(context, left, right); 7471 instr = new(zone()) HStringAdd(context, left, right);
7461 } else { 7472 } else {
7462 instr = HAdd::NewHAdd(zone(), context, left, right); 7473 instr = HAdd::NewHAdd(zone(), context, left, right);
7463 } 7474 }
7464 break; 7475 break;
7465 case Token::SUB: 7476 case Token::SUB:
7466 instr = HSub::NewHSub(zone(), context, left, right); 7477 instr = HSub::NewHSub(zone(), context, left, right);
7467 break; 7478 break;
7468 case Token::MUL: 7479 case Token::MUL:
7469 instr = HMul::NewHMul(zone(), context, left, right); 7480 instr = HMul::NewHMul(zone(), context, left, right);
(...skipping 379 matching lines...)
7849 result->set_position(expr->position()); 7860 result->set_position(expr->position());
7850 return ast_context()->ReturnInstruction(result, expr->id()); 7861 return ast_context()->ReturnInstruction(result, expr->id());
7851 } else if (type_info.IsNonPrimitive()) { 7862 } else if (type_info.IsNonPrimitive()) {
7852 switch (op) { 7863 switch (op) {
7853 case Token::EQ: 7864 case Token::EQ:
7854 case Token::EQ_STRICT: { 7865 case Token::EQ_STRICT: {
7855 // Can we get away with map check and not instance type check? 7866 // Can we get away with map check and not instance type check?
7856 Handle<Map> map = oracle()->GetCompareMap(expr); 7867 Handle<Map> map = oracle()->GetCompareMap(expr);
7857 if (!map.is_null()) { 7868 if (!map.is_null()) {
7858 AddInstruction(new(zone()) HCheckNonSmi(left)); 7869 AddInstruction(new(zone()) HCheckNonSmi(left));
7859 AddInstruction(HCheckMaps::NewWithTransitions(left, map)); 7870 AddInstruction(HCheckMaps::NewWithTransitions(left, map, zone()));
7860 AddInstruction(new(zone()) HCheckNonSmi(right)); 7871 AddInstruction(new(zone()) HCheckNonSmi(right));
7861 AddInstruction(HCheckMaps::NewWithTransitions(right, map)); 7872 AddInstruction(HCheckMaps::NewWithTransitions(right, map, zone()));
7862 HCompareObjectEqAndBranch* result = 7873 HCompareObjectEqAndBranch* result =
7863 new(zone()) HCompareObjectEqAndBranch(left, right); 7874 new(zone()) HCompareObjectEqAndBranch(left, right);
7864 result->set_position(expr->position()); 7875 result->set_position(expr->position());
7865 return ast_context()->ReturnControl(result, expr->id()); 7876 return ast_context()->ReturnControl(result, expr->id());
7866 } else { 7877 } else {
7867 AddInstruction(new(zone()) HCheckNonSmi(left)); 7878 AddInstruction(new(zone()) HCheckNonSmi(left));
7868 AddInstruction(HCheckInstanceType::NewIsSpecObject(left)); 7879 AddInstruction(HCheckInstanceType::NewIsSpecObject(left, zone()));
7869 AddInstruction(new(zone()) HCheckNonSmi(right)); 7880 AddInstruction(new(zone()) HCheckNonSmi(right));
7870 AddInstruction(HCheckInstanceType::NewIsSpecObject(right)); 7881 AddInstruction(HCheckInstanceType::NewIsSpecObject(right, zone()));
7871 HCompareObjectEqAndBranch* result = 7882 HCompareObjectEqAndBranch* result =
7872 new(zone()) HCompareObjectEqAndBranch(left, right); 7883 new(zone()) HCompareObjectEqAndBranch(left, right);
7873 result->set_position(expr->position()); 7884 result->set_position(expr->position());
7874 return ast_context()->ReturnControl(result, expr->id()); 7885 return ast_context()->ReturnControl(result, expr->id());
7875 } 7886 }
7876 } 7887 }
7877 default: 7888 default:
7878 return Bailout("Unsupported non-primitive compare"); 7889 return Bailout("Unsupported non-primitive compare");
7879 } 7890 }
7880 } else if (type_info.IsString() && oracle()->IsSymbolCompare(expr) && 7891 } else if (type_info.IsString() && oracle()->IsSymbolCompare(expr) &&
7881 (op == Token::EQ || op == Token::EQ_STRICT)) { 7892 (op == Token::EQ || op == Token::EQ_STRICT)) {
7882 AddInstruction(new(zone()) HCheckNonSmi(left)); 7893 AddInstruction(new(zone()) HCheckNonSmi(left));
7883 AddInstruction(HCheckInstanceType::NewIsSymbol(left)); 7894 AddInstruction(HCheckInstanceType::NewIsSymbol(left, zone()));
7884 AddInstruction(new(zone()) HCheckNonSmi(right)); 7895 AddInstruction(new(zone()) HCheckNonSmi(right));
7885 AddInstruction(HCheckInstanceType::NewIsSymbol(right)); 7896 AddInstruction(HCheckInstanceType::NewIsSymbol(right, zone()));
7886 HCompareObjectEqAndBranch* result = 7897 HCompareObjectEqAndBranch* result =
7887 new(zone()) HCompareObjectEqAndBranch(left, right); 7898 new(zone()) HCompareObjectEqAndBranch(left, right);
7888 result->set_position(expr->position()); 7899 result->set_position(expr->position());
7889 return ast_context()->ReturnControl(result, expr->id()); 7900 return ast_context()->ReturnControl(result, expr->id());
7890 } else { 7901 } else {
7891 Representation r = ToRepresentation(type_info); 7902 Representation r = ToRepresentation(type_info);
7892 if (r.IsTagged()) { 7903 if (r.IsTagged()) {
7893 HCompareGeneric* result = 7904 HCompareGeneric* result =
7894 new(zone()) HCompareGeneric(context, left, right, op); 7905 new(zone()) HCompareGeneric(context, left, right, op);
7895 result->set_position(expr->position()); 7906 result->set_position(expr->position());
(...skipping 51 matching lines...)
7947 } 7958 }
7948 7959
7949 7960
7950 void HGraphBuilder::VisitVariableDeclaration(VariableDeclaration* declaration) { 7961 void HGraphBuilder::VisitVariableDeclaration(VariableDeclaration* declaration) {
7951 VariableProxy* proxy = declaration->proxy(); 7962 VariableProxy* proxy = declaration->proxy();
7952 VariableMode mode = declaration->mode(); 7963 VariableMode mode = declaration->mode();
7953 Variable* variable = proxy->var(); 7964 Variable* variable = proxy->var();
7954 bool hole_init = mode == CONST || mode == CONST_HARMONY || mode == LET; 7965 bool hole_init = mode == CONST || mode == CONST_HARMONY || mode == LET;
7955 switch (variable->location()) { 7966 switch (variable->location()) {
7956 case Variable::UNALLOCATED: 7967 case Variable::UNALLOCATED:
7957 globals_.Add(variable->name()); 7968 globals_.Add(variable->name(), zone());
7958 globals_.Add(variable->binding_needs_init() 7969 globals_.Add(variable->binding_needs_init()
7959 ? isolate()->factory()->the_hole_value() 7970 ? isolate()->factory()->the_hole_value()
7960 : isolate()->factory()->undefined_value()); 7971 : isolate()->factory()->undefined_value(), zone());
7961 return; 7972 return;
7962 case Variable::PARAMETER: 7973 case Variable::PARAMETER:
7963 case Variable::LOCAL: 7974 case Variable::LOCAL:
7964 if (hole_init) { 7975 if (hole_init) {
7965 HValue* value = graph()->GetConstantHole(); 7976 HValue* value = graph()->GetConstantHole();
7966 environment()->Bind(variable, value); 7977 environment()->Bind(variable, value);
7967 } 7978 }
7968 break; 7979 break;
7969 case Variable::CONTEXT: 7980 case Variable::CONTEXT:
7970 if (hole_init) { 7981 if (hole_init) {
7971 HValue* value = graph()->GetConstantHole(); 7982 HValue* value = graph()->GetConstantHole();
7972 HValue* context = environment()->LookupContext(); 7983 HValue* context = environment()->LookupContext();
7973 HStoreContextSlot* store = new HStoreContextSlot( 7984 HStoreContextSlot* store = new(zone()) HStoreContextSlot(
7974 context, variable->index(), HStoreContextSlot::kNoCheck, value); 7985 context, variable->index(), HStoreContextSlot::kNoCheck, value);
7975 AddInstruction(store); 7986 AddInstruction(store);
7976 if (store->HasObservableSideEffects()) AddSimulate(proxy->id()); 7987 if (store->HasObservableSideEffects()) AddSimulate(proxy->id());
7977 } 7988 }
7978 break; 7989 break;
7979 case Variable::LOOKUP: 7990 case Variable::LOOKUP:
7980 return Bailout("unsupported lookup slot in declaration"); 7991 return Bailout("unsupported lookup slot in declaration");
7981 } 7992 }
7982 } 7993 }
7983 7994
7984 7995
7985 void HGraphBuilder::VisitFunctionDeclaration(FunctionDeclaration* declaration) { 7996 void HGraphBuilder::VisitFunctionDeclaration(FunctionDeclaration* declaration) {
7986 VariableProxy* proxy = declaration->proxy(); 7997 VariableProxy* proxy = declaration->proxy();
7987 Variable* variable = proxy->var(); 7998 Variable* variable = proxy->var();
7988 switch (variable->location()) { 7999 switch (variable->location()) {
7989 case Variable::UNALLOCATED: { 8000 case Variable::UNALLOCATED: {
7990 globals_.Add(variable->name()); 8001 globals_.Add(variable->name(), zone());
7991 Handle<SharedFunctionInfo> function = 8002 Handle<SharedFunctionInfo> function =
7992 Compiler::BuildFunctionInfo(declaration->fun(), info()->script()); 8003 Compiler::BuildFunctionInfo(declaration->fun(), info()->script());
7993 // Check for stack-overflow exception. 8004 // Check for stack-overflow exception.
7994 if (function.is_null()) return SetStackOverflow(); 8005 if (function.is_null()) return SetStackOverflow();
7995 globals_.Add(function); 8006 globals_.Add(function, zone());
7996 return; 8007 return;
7997 } 8008 }
7998 case Variable::PARAMETER: 8009 case Variable::PARAMETER:
7999 case Variable::LOCAL: { 8010 case Variable::LOCAL: {
8000 CHECK_ALIVE(VisitForValue(declaration->fun())); 8011 CHECK_ALIVE(VisitForValue(declaration->fun()));
8001 HValue* value = Pop(); 8012 HValue* value = Pop();
8002 environment()->Bind(variable, value); 8013 environment()->Bind(variable, value);
8003 break; 8014 break;
8004 } 8015 }
8005 case Variable::CONTEXT: { 8016 case Variable::CONTEXT: {
8006 CHECK_ALIVE(VisitForValue(declaration->fun())); 8017 CHECK_ALIVE(VisitForValue(declaration->fun()));
8007 HValue* value = Pop(); 8018 HValue* value = Pop();
8008 HValue* context = environment()->LookupContext(); 8019 HValue* context = environment()->LookupContext();
8009 HStoreContextSlot* store = new HStoreContextSlot( 8020 HStoreContextSlot* store = new(zone()) HStoreContextSlot(
8010 context, variable->index(), HStoreContextSlot::kNoCheck, value); 8021 context, variable->index(), HStoreContextSlot::kNoCheck, value);
8011 AddInstruction(store); 8022 AddInstruction(store);
8012 if (store->HasObservableSideEffects()) AddSimulate(proxy->id()); 8023 if (store->HasObservableSideEffects()) AddSimulate(proxy->id());
8013 break; 8024 break;
8014 } 8025 }
8015 case Variable::LOOKUP: 8026 case Variable::LOOKUP:
8016 return Bailout("unsupported lookup slot in declaration"); 8027 return Bailout("unsupported lookup slot in declaration");
8017 } 8028 }
8018 } 8029 }
8019 8030
(...skipping 225 matching lines...)
8245 HBasicBlock* if_js_value = graph()->CreateBasicBlock(); 8256 HBasicBlock* if_js_value = graph()->CreateBasicBlock();
8246 HBasicBlock* not_js_value = graph()->CreateBasicBlock(); 8257 HBasicBlock* not_js_value = graph()->CreateBasicBlock();
8247 typecheck->SetSuccessorAt(0, if_js_value); 8258 typecheck->SetSuccessorAt(0, if_js_value);
8248 typecheck->SetSuccessorAt(1, not_js_value); 8259 typecheck->SetSuccessorAt(1, not_js_value);
8249 current_block()->Finish(typecheck); 8260 current_block()->Finish(typecheck);
8250 not_js_value->Goto(join); 8261 not_js_value->Goto(join);
8251 8262
8252 // Create in-object property store to kValueOffset. 8263 // Create in-object property store to kValueOffset.
8253 set_current_block(if_js_value); 8264 set_current_block(if_js_value);
8254 Handle<String> name = isolate()->factory()->undefined_symbol(); 8265 Handle<String> name = isolate()->factory()->undefined_symbol();
8255 AddInstruction(new HStoreNamedField(object, 8266 AddInstruction(new(zone()) HStoreNamedField(object,
8256 name, 8267 name,
8257 value, 8268 value,
8258 true, // in-object store. 8269 true, // in-object store.
8259 JSValue::kValueOffset)); 8270 JSValue::kValueOffset));
8260 if_js_value->Goto(join); 8271 if_js_value->Goto(join);
8261 join->SetJoinId(call->id()); 8272 join->SetJoinId(call->id());
8262 set_current_block(join); 8273 set_current_block(join);
8263 return ast_context()->ReturnValue(value); 8274 return ast_context()->ReturnValue(value);
8264 } 8275 }
8265 8276
8266 8277
8267 // Fast support for charCodeAt(n). 8278 // Fast support for charCodeAt(n).
8268 void HGraphBuilder::GenerateStringCharCodeAt(CallRuntime* call) { 8279 void HGraphBuilder::GenerateStringCharCodeAt(CallRuntime* call) {
8269 ASSERT(call->arguments()->length() == 2); 8280 ASSERT(call->arguments()->length() == 2);
(...skipping 267 matching lines...)
8537 return Bailout("inlined runtime function: FastAsciiArrayJoin"); 8548 return Bailout("inlined runtime function: FastAsciiArrayJoin");
8538 } 8549 }
8539 8550
8540 8551
8541 #undef CHECK_BAILOUT 8552 #undef CHECK_BAILOUT
8542 #undef CHECK_ALIVE 8553 #undef CHECK_ALIVE
8543 8554
8544 8555
8545 HEnvironment::HEnvironment(HEnvironment* outer, 8556 HEnvironment::HEnvironment(HEnvironment* outer,
8546 Scope* scope, 8557 Scope* scope,
8547 Handle<JSFunction> closure) 8558 Handle<JSFunction> closure,
8559 Zone* zone)
8548 : closure_(closure), 8560 : closure_(closure),
8549 values_(0), 8561 values_(0, zone),
8550 assigned_variables_(4), 8562 assigned_variables_(4, zone),
8551 frame_type_(JS_FUNCTION), 8563 frame_type_(JS_FUNCTION),
8552 parameter_count_(0), 8564 parameter_count_(0),
8553 specials_count_(1), 8565 specials_count_(1),
8554 local_count_(0), 8566 local_count_(0),
8555 outer_(outer), 8567 outer_(outer),
8556 pop_count_(0), 8568 pop_count_(0),
8557 push_count_(0), 8569 push_count_(0),
8558 ast_id_(AstNode::kNoNumber) { 8570 ast_id_(AstNode::kNoNumber),
8571 zone_(zone) {
8559 Initialize(scope->num_parameters() + 1, scope->num_stack_slots(), 0); 8572 Initialize(scope->num_parameters() + 1, scope->num_stack_slots(), 0);
8560 } 8573 }
8561 8574
8562 8575
8563 HEnvironment::HEnvironment(const HEnvironment* other) 8576 HEnvironment::HEnvironment(const HEnvironment* other, Zone* zone)
8564 : values_(0), 8577 : values_(0, zone),
8565 assigned_variables_(0), 8578 assigned_variables_(0, zone),
8566 frame_type_(JS_FUNCTION), 8579 frame_type_(JS_FUNCTION),
8567 parameter_count_(0), 8580 parameter_count_(0),
8568 specials_count_(1), 8581 specials_count_(1),
8569 local_count_(0), 8582 local_count_(0),
8570 outer_(NULL), 8583 outer_(NULL),
8571 pop_count_(0), 8584 pop_count_(0),
8572 push_count_(0), 8585 push_count_(0),
8573 ast_id_(other->ast_id()) { 8586 ast_id_(other->ast_id()),
8587 zone_(zone) {
8574 Initialize(other); 8588 Initialize(other);
8575 } 8589 }
8576 8590
8577 8591
8578 HEnvironment::HEnvironment(HEnvironment* outer, 8592 HEnvironment::HEnvironment(HEnvironment* outer,
8579 Handle<JSFunction> closure, 8593 Handle<JSFunction> closure,
8580 FrameType frame_type, 8594 FrameType frame_type,
8581 int arguments) 8595 int arguments,
8596 Zone* zone)
8582 : closure_(closure), 8597 : closure_(closure),
8583 values_(arguments), 8598 values_(arguments, zone),
8584 assigned_variables_(0), 8599 assigned_variables_(0, zone),
8585 frame_type_(frame_type), 8600 frame_type_(frame_type),
8586 parameter_count_(arguments), 8601 parameter_count_(arguments),
8587 local_count_(0), 8602 local_count_(0),
8588 outer_(outer), 8603 outer_(outer),
8589 pop_count_(0), 8604 pop_count_(0),
8590 push_count_(0), 8605 push_count_(0),
8591 ast_id_(AstNode::kNoNumber) { 8606 ast_id_(AstNode::kNoNumber),
8607 zone_(zone) {
8592 } 8608 }
8593 8609
8594 8610
8595 void HEnvironment::Initialize(int parameter_count, 8611 void HEnvironment::Initialize(int parameter_count,
8596 int local_count, 8612 int local_count,
8597 int stack_height) { 8613 int stack_height) {
8598 parameter_count_ = parameter_count; 8614 parameter_count_ = parameter_count;
8599 local_count_ = local_count; 8615 local_count_ = local_count;
8600 8616
8601 // Avoid reallocating the temporaries' backing store on the first Push. 8617 // Avoid reallocating the temporaries' backing store on the first Push.
8602 int total = parameter_count + specials_count_ + local_count + stack_height; 8618 int total = parameter_count + specials_count_ + local_count + stack_height;
8603 values_.Initialize(total + 4); 8619 values_.Initialize(total + 4, zone());
8604 for (int i = 0; i < total; ++i) values_.Add(NULL); 8620 for (int i = 0; i < total; ++i) values_.Add(NULL, zone());
8605 } 8621 }
8606 8622
8607 8623
8608 void HEnvironment::Initialize(const HEnvironment* other) { 8624 void HEnvironment::Initialize(const HEnvironment* other) {
8609 closure_ = other->closure(); 8625 closure_ = other->closure();
8610 values_.AddAll(other->values_); 8626 values_.AddAll(other->values_, zone());
8611 assigned_variables_.AddAll(other->assigned_variables_); 8627 assigned_variables_.AddAll(other->assigned_variables_, zone());
8612 frame_type_ = other->frame_type_; 8628 frame_type_ = other->frame_type_;
8613 parameter_count_ = other->parameter_count_; 8629 parameter_count_ = other->parameter_count_;
8614 local_count_ = other->local_count_; 8630 local_count_ = other->local_count_;
8615 if (other->outer_ != NULL) outer_ = other->outer_->Copy(); // Deep copy. 8631 if (other->outer_ != NULL) outer_ = other->outer_->Copy(); // Deep copy.
8616 pop_count_ = other->pop_count_; 8632 pop_count_ = other->pop_count_;
8617 push_count_ = other->push_count_; 8633 push_count_ = other->push_count_;
8618 ast_id_ = other->ast_id_; 8634 ast_id_ = other->ast_id_;
8619 } 8635 }
8620 8636
8621 8637
8622 void HEnvironment::AddIncomingEdge(HBasicBlock* block, HEnvironment* other) { 8638 void HEnvironment::AddIncomingEdge(HBasicBlock* block, HEnvironment* other) {
8623 ASSERT(!block->IsLoopHeader()); 8639 ASSERT(!block->IsLoopHeader());
8624 ASSERT(values_.length() == other->values_.length()); 8640 ASSERT(values_.length() == other->values_.length());
8625 8641
8626 int length = values_.length(); 8642 int length = values_.length();
8627 for (int i = 0; i < length; ++i) { 8643 for (int i = 0; i < length; ++i) {
8628 HValue* value = values_[i]; 8644 HValue* value = values_[i];
8629 if (value != NULL && value->IsPhi() && value->block() == block) { 8645 if (value != NULL && value->IsPhi() && value->block() == block) {
8630 // There is already a phi for the i'th value. 8646 // There is already a phi for the i'th value.
8631 HPhi* phi = HPhi::cast(value); 8647 HPhi* phi = HPhi::cast(value);
8632 // Assert index is correct and that we haven't missed an incoming edge. 8648 // Assert index is correct and that we haven't missed an incoming edge.
8633 ASSERT(phi->merged_index() == i); 8649 ASSERT(phi->merged_index() == i);
8634 ASSERT(phi->OperandCount() == block->predecessors()->length()); 8650 ASSERT(phi->OperandCount() == block->predecessors()->length());
8635 phi->AddInput(other->values_[i]); 8651 phi->AddInput(other->values_[i]);
8636 } else if (values_[i] != other->values_[i]) { 8652 } else if (values_[i] != other->values_[i]) {
8637 // There is a fresh value on the incoming edge, a phi is needed. 8653 // There is a fresh value on the incoming edge, a phi is needed.
8638 ASSERT(values_[i] != NULL && other->values_[i] != NULL); 8654 ASSERT(values_[i] != NULL && other->values_[i] != NULL);
8639 HPhi* phi = new(block->zone()) HPhi(i); 8655 HPhi* phi = new(zone()) HPhi(i, zone());
8640 HValue* old_value = values_[i]; 8656 HValue* old_value = values_[i];
8641 for (int j = 0; j < block->predecessors()->length(); j++) { 8657 for (int j = 0; j < block->predecessors()->length(); j++) {
8642 phi->AddInput(old_value); 8658 phi->AddInput(old_value);
8643 } 8659 }
8644 phi->AddInput(other->values_[i]); 8660 phi->AddInput(other->values_[i]);
8645 this->values_[i] = phi; 8661 this->values_[i] = phi;
8646 block->AddPhi(phi); 8662 block->AddPhi(phi);
8647 } 8663 }
8648 } 8664 }
8649 } 8665 }
8650 8666
8651 8667
8652 void HEnvironment::Bind(int index, HValue* value) { 8668 void HEnvironment::Bind(int index, HValue* value) {
8653 ASSERT(value != NULL); 8669 ASSERT(value != NULL);
8654 if (!assigned_variables_.Contains(index)) { 8670 if (!assigned_variables_.Contains(index)) {
8655 assigned_variables_.Add(index); 8671 assigned_variables_.Add(index, zone());
8656 } 8672 }
8657 values_[index] = value; 8673 values_[index] = value;
8658 } 8674 }
8659 8675
8660 8676
8661 bool HEnvironment::HasExpressionAt(int index) const { 8677 bool HEnvironment::HasExpressionAt(int index) const {
8662 return index >= parameter_count_ + specials_count_ + local_count_; 8678 return index >= parameter_count_ + specials_count_ + local_count_;
8663 } 8679 }
8664 8680
8665 8681
(...skipping 19 matching lines...)
8685 8701
8686 8702
8687 void HEnvironment::Drop(int count) { 8703 void HEnvironment::Drop(int count) {
8688 for (int i = 0; i < count; ++i) { 8704 for (int i = 0; i < count; ++i) {
8689 Pop(); 8705 Pop();
8690 } 8706 }
8691 } 8707 }
8692 8708
8693 8709
8694 HEnvironment* HEnvironment::Copy() const { 8710 HEnvironment* HEnvironment::Copy() const {
8695 return new(closure()->GetIsolate()->zone()) HEnvironment(this); 8711 return new(zone()) HEnvironment(this, zone());
8696 } 8712 }
8697 8713
8698 8714
8699 HEnvironment* HEnvironment::CopyWithoutHistory() const { 8715 HEnvironment* HEnvironment::CopyWithoutHistory() const {
8700 HEnvironment* result = Copy(); 8716 HEnvironment* result = Copy();
8701 result->ClearHistory(); 8717 result->ClearHistory();
8702 return result; 8718 return result;
8703 } 8719 }
8704 8720
8705 8721
8706 HEnvironment* HEnvironment::CopyAsLoopHeader(HBasicBlock* loop_header) const { 8722 HEnvironment* HEnvironment::CopyAsLoopHeader(HBasicBlock* loop_header) const {
8707 HEnvironment* new_env = Copy(); 8723 HEnvironment* new_env = Copy();
8708 for (int i = 0; i < values_.length(); ++i) { 8724 for (int i = 0; i < values_.length(); ++i) {
8709 HPhi* phi = new(loop_header->zone()) HPhi(i); 8725 HPhi* phi = new(zone()) HPhi(i, zone());
8710 phi->AddInput(values_[i]); 8726 phi->AddInput(values_[i]);
8711 new_env->values_[i] = phi; 8727 new_env->values_[i] = phi;
8712 loop_header->AddPhi(phi); 8728 loop_header->AddPhi(phi);
8713 } 8729 }
8714 new_env->ClearHistory(); 8730 new_env->ClearHistory();
8715 return new_env; 8731 return new_env;
8716 } 8732 }
8717 8733
8718 8734
8719 HEnvironment* HEnvironment::CreateStubEnvironment(HEnvironment* outer, 8735 HEnvironment* HEnvironment::CreateStubEnvironment(HEnvironment* outer,
8720 Handle<JSFunction> target, 8736 Handle<JSFunction> target,
8721 FrameType frame_type, 8737 FrameType frame_type,
8722 int arguments) const { 8738 int arguments) const {
8723 HEnvironment* new_env = new(closure()->GetIsolate()->zone()) 8739 HEnvironment* new_env =
8724 HEnvironment(outer, target, frame_type, arguments + 1); 8740 new(zone()) HEnvironment(outer, target, frame_type,
8741 arguments + 1, zone());
8725 for (int i = 0; i <= arguments; ++i) { // Include receiver. 8742 for (int i = 0; i <= arguments; ++i) { // Include receiver.
8726 new_env->Push(ExpressionStackAt(arguments - i)); 8743 new_env->Push(ExpressionStackAt(arguments - i));
8727 } 8744 }
8728 new_env->ClearHistory(); 8745 new_env->ClearHistory();
8729 return new_env; 8746 return new_env;
8730 } 8747 }
8731 8748
8732 8749
8733 HEnvironment* HEnvironment::CopyForInlining( 8750 HEnvironment* HEnvironment::CopyForInlining(
8734 Handle<JSFunction> target, 8751 Handle<JSFunction> target,
(...skipping 19 matching lines...)
8754 // object instead, DoComputeConstructStubFrame() relies on that. 8771 // object instead, DoComputeConstructStubFrame() relies on that.
8755 outer = CreateStubEnvironment(outer, target, JS_CONSTRUCT, arguments); 8772 outer = CreateStubEnvironment(outer, target, JS_CONSTRUCT, arguments);
8756 } 8773 }
8757 8774
8758 if (arity != arguments) { 8775 if (arity != arguments) {
8759 // Create artificial arguments adaptation environment. 8776 // Create artificial arguments adaptation environment.
8760 outer = CreateStubEnvironment(outer, target, ARGUMENTS_ADAPTOR, arguments); 8777 outer = CreateStubEnvironment(outer, target, ARGUMENTS_ADAPTOR, arguments);
8761 } 8778 }
8762 8779
8763 HEnvironment* inner = 8780 HEnvironment* inner =
8764 new(zone) HEnvironment(outer, function->scope(), target); 8781 new(zone) HEnvironment(outer, function->scope(), target, zone);
8765 // Get the argument values from the original environment. 8782 // Get the argument values from the original environment.
8766 for (int i = 0; i <= arity; ++i) { // Include receiver. 8783 for (int i = 0; i <= arity; ++i) { // Include receiver.
8767 HValue* push = (i <= arguments) ? 8784 HValue* push = (i <= arguments) ?
8768 ExpressionStackAt(arguments - i) : undefined; 8785 ExpressionStackAt(arguments - i) : undefined;
8769 inner->SetValueAt(i, push); 8786 inner->SetValueAt(i, push);
8770 } 8787 }
8771 // If the function we are inlining is a strict mode function or a 8788 // If the function we are inlining is a strict mode function or a
8772 // builtin function, pass undefined as the receiver for function 8789 // builtin function, pass undefined as the receiver for function
8773 // calls (instead of the global receiver). 8790 // calls (instead of the global receiver).
8774 if ((target->shared()->native() || !function->is_classic_mode()) && 8791 if ((target->shared()->native() || !function->is_classic_mode()) &&
(...skipping 169 matching lines...)
8944 } 8961 }
8945 } 8962 }
8946 8963
8947 8964
8948 void HTracer::TraceLiveRanges(const char* name, LAllocator* allocator) { 8965 void HTracer::TraceLiveRanges(const char* name, LAllocator* allocator) {
8949 Tag tag(this, "intervals"); 8966 Tag tag(this, "intervals");
8950 PrintStringProperty("name", name); 8967 PrintStringProperty("name", name);
8951 8968
8952 const Vector<LiveRange*>* fixed_d = allocator->fixed_double_live_ranges(); 8969 const Vector<LiveRange*>* fixed_d = allocator->fixed_double_live_ranges();
8953 for (int i = 0; i < fixed_d->length(); ++i) { 8970 for (int i = 0; i < fixed_d->length(); ++i) {
8954 TraceLiveRange(fixed_d->at(i), "fixed"); 8971 TraceLiveRange(fixed_d->at(i), "fixed", allocator->zone());
8955 } 8972 }
8956 8973
8957 const Vector<LiveRange*>* fixed = allocator->fixed_live_ranges(); 8974 const Vector<LiveRange*>* fixed = allocator->fixed_live_ranges();
8958 for (int i = 0; i < fixed->length(); ++i) { 8975 for (int i = 0; i < fixed->length(); ++i) {
8959 TraceLiveRange(fixed->at(i), "fixed"); 8976 TraceLiveRange(fixed->at(i), "fixed", allocator->zone());
8960 } 8977 }
8961 8978
8962 const ZoneList<LiveRange*>* live_ranges = allocator->live_ranges(); 8979 const ZoneList<LiveRange*>* live_ranges = allocator->live_ranges();
8963 for (int i = 0; i < live_ranges->length(); ++i) { 8980 for (int i = 0; i < live_ranges->length(); ++i) {
8964 TraceLiveRange(live_ranges->at(i), "object"); 8981 TraceLiveRange(live_ranges->at(i), "object", allocator->zone());
8965 } 8982 }
8966 } 8983 }
8967 8984
8968 8985
8969 void HTracer::TraceLiveRange(LiveRange* range, const char* type) { 8986 void HTracer::TraceLiveRange(LiveRange* range, const char* type,
8987 Zone* zone) {
8970 if (range != NULL && !range->IsEmpty()) { 8988 if (range != NULL && !range->IsEmpty()) {
8971 PrintIndent(); 8989 PrintIndent();
8972 trace_.Add("%d %s", range->id(), type); 8990 trace_.Add("%d %s", range->id(), type);
8973 if (range->HasRegisterAssigned()) { 8991 if (range->HasRegisterAssigned()) {
8974 LOperand* op = range->CreateAssignedOperand(ZONE); 8992 LOperand* op = range->CreateAssignedOperand(zone);
8975 int assigned_reg = op->index(); 8993 int assigned_reg = op->index();
8976 if (op->IsDoubleRegister()) { 8994 if (op->IsDoubleRegister()) {
8977 trace_.Add(" \"%s\"", 8995 trace_.Add(" \"%s\"",
8978 DoubleRegister::AllocationIndexToString(assigned_reg)); 8996 DoubleRegister::AllocationIndexToString(assigned_reg));
8979 } else { 8997 } else {
8980 ASSERT(op->IsRegister()); 8998 ASSERT(op->IsRegister());
8981 trace_.Add(" \"%s\"", Register::AllocationIndexToString(assigned_reg)); 8999 trace_.Add(" \"%s\"", Register::AllocationIndexToString(assigned_reg));
8982 } 9000 }
8983 } else if (range->IsSpilled()) { 9001 } else if (range->IsSpilled()) {
8984 LOperand* op = range->TopLevel()->GetSpillOperand(); 9002 LOperand* op = range->TopLevel()->GetSpillOperand();
(...skipping 141 matching lines...)
9126 } 9144 }
9127 } 9145 }
9128 9146
9129 #ifdef DEBUG 9147 #ifdef DEBUG
9130 if (graph_ != NULL) graph_->Verify(false); // No full verify. 9148 if (graph_ != NULL) graph_->Verify(false); // No full verify.
9131 if (allocator_ != NULL) allocator_->Verify(); 9149 if (allocator_ != NULL) allocator_->Verify();
9132 #endif 9150 #endif
9133 } 9151 }
9134 9152
9135 } } // namespace v8::internal 9153 } } // namespace v8::internal
OLDNEW

Powered by Google App Engine