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

Side by Side Diff: src/hydrogen.h

Issue 6697023: Merge 6800:7180 from the bleeding edge branch to the experimental/gc branch. (Closed) Base URL: http://v8.googlecode.com/svn/branches/experimental/gc/
Patch Set: Created 9 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/heap-profiler.cc ('k') | src/hydrogen.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2011 the V8 project authors. All rights reserved. 1 // Copyright 2011 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after
110 void set_parent_loop_header(HBasicBlock* block) { 110 void set_parent_loop_header(HBasicBlock* block) {
111 ASSERT(parent_loop_header_ == NULL); 111 ASSERT(parent_loop_header_ == NULL);
112 parent_loop_header_ = block; 112 parent_loop_header_ = block;
113 } 113 }
114 114
115 bool HasParentLoopHeader() const { return parent_loop_header_ != NULL; } 115 bool HasParentLoopHeader() const { return parent_loop_header_ != NULL; }
116 116
117 void SetJoinId(int id); 117 void SetJoinId(int id);
118 118
119 void Finish(HControlInstruction* last); 119 void Finish(HControlInstruction* last);
120 void FinishExit(HControlInstruction* instruction);
120 void Goto(HBasicBlock* block, bool include_stack_check = false); 121 void Goto(HBasicBlock* block, bool include_stack_check = false);
121 122
122 int PredecessorIndexOf(HBasicBlock* predecessor) const; 123 int PredecessorIndexOf(HBasicBlock* predecessor) const;
123 void AddSimulate(int id) { AddInstruction(CreateSimulate(id)); } 124 void AddSimulate(int id) { AddInstruction(CreateSimulate(id)); }
124 void AssignCommonDominator(HBasicBlock* other); 125 void AssignCommonDominator(HBasicBlock* other);
125 126
126 // Add the inlined function exit sequence, adding an HLeaveInlined 127 // Add the inlined function exit sequence, adding an HLeaveInlined
127 // instruction and updating the bailout environment. 128 // instruction and updating the bailout environment.
128 void AddLeaveInlined(HValue* return_value, HBasicBlock* target); 129 void AddLeaveInlined(HValue* return_value, HBasicBlock* target);
129 130
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
184 185
185 private: 186 private:
186 void AddBlock(HBasicBlock* block); 187 void AddBlock(HBasicBlock* block);
187 188
188 ZoneList<HBasicBlock*> back_edges_; 189 ZoneList<HBasicBlock*> back_edges_;
189 HBasicBlock* loop_header_; 190 HBasicBlock* loop_header_;
190 ZoneList<HBasicBlock*> blocks_; 191 ZoneList<HBasicBlock*> blocks_;
191 }; 192 };
192 193
193 194
194 class HSubgraph: public ZoneObject { 195 class HGraph: public ZoneObject {
195 public:
196 explicit HSubgraph(HGraph* graph)
197 : graph_(graph),
198 entry_block_(NULL),
199 exit_block_(NULL),
200 break_continue_info_(4) {
201 }
202
203 HGraph* graph() const { return graph_; }
204 HEnvironment* environment() const {
205 ASSERT(HasExit());
206 return exit_block_->last_environment();
207 }
208
209 bool HasExit() const { return exit_block_ != NULL; }
210
211 void PreProcessOsrEntry(IterationStatement* statement);
212
213 void AppendOptional(HSubgraph* graph,
214 bool on_true_branch,
215 HValue* boolean_value);
216 void AppendJoin(HSubgraph* then_graph, HSubgraph* else_graph, AstNode* node);
217 void AppendWhile(HSubgraph* condition,
218 HSubgraph* body,
219 IterationStatement* statement,
220 HSubgraph* continue_subgraph,
221 HSubgraph* exit);
222 void AppendDoWhile(HSubgraph* body,
223 IterationStatement* statement,
224 HSubgraph* go_back,
225 HSubgraph* exit);
226 void AppendEndless(HSubgraph* body, IterationStatement* statement);
227 void Append(HSubgraph* next, BreakableStatement* statement);
228 void ResolveContinue(IterationStatement* statement);
229 HBasicBlock* BundleBreak(BreakableStatement* statement);
230 HBasicBlock* BundleContinue(IterationStatement* statement);
231 HBasicBlock* BundleBreakContinue(BreakableStatement* statement,
232 bool is_continue,
233 int join_id);
234 HBasicBlock* JoinBlocks(HBasicBlock* a, HBasicBlock* b, int id);
235
236 void FinishExit(HControlInstruction* instruction);
237 void FinishBreakContinue(BreakableStatement* target, bool is_continue);
238 void Initialize(HBasicBlock* block) {
239 ASSERT(entry_block_ == NULL);
240 entry_block_ = block;
241 exit_block_ = block;
242 }
243 HBasicBlock* entry_block() const { return entry_block_; }
244 HBasicBlock* exit_block() const { return exit_block_; }
245 void set_exit_block(HBasicBlock* block) {
246 exit_block_ = block;
247 }
248
249 void ConnectExitTo(HBasicBlock* other, bool include_stack_check = false) {
250 if (HasExit()) {
251 exit_block()->Goto(other, include_stack_check);
252 }
253 }
254
255 void AddBreakContinueInfo(HSubgraph* other) {
256 break_continue_info_.AddAll(other->break_continue_info_);
257 }
258
259 protected:
260 class BreakContinueInfo: public ZoneObject {
261 public:
262 BreakContinueInfo(BreakableStatement* target, HBasicBlock* block,
263 bool is_continue)
264 : target_(target), block_(block), continue_(is_continue) {}
265 BreakableStatement* target() const { return target_; }
266 HBasicBlock* block() const { return block_; }
267 bool is_continue() const { return continue_; }
268 bool IsResolved() const { return block_ == NULL; }
269 void Resolve() { block_ = NULL; }
270
271 private:
272 BreakableStatement* target_;
273 HBasicBlock* block_;
274 bool continue_;
275 };
276
277 const ZoneList<BreakContinueInfo*>* break_continue_info() const {
278 return &break_continue_info_;
279 }
280
281 HGraph* graph_; // The graph this is a subgraph of.
282 HBasicBlock* entry_block_;
283 HBasicBlock* exit_block_;
284
285 private:
286 ZoneList<BreakContinueInfo*> break_continue_info_;
287 };
288
289
290 class HGraph: public HSubgraph {
291 public: 196 public:
292 explicit HGraph(CompilationInfo* info); 197 explicit HGraph(CompilationInfo* info);
293 198
294 CompilationInfo* info() const { return info_; }
295
296 bool AllowCodeMotion() const;
297
298 const ZoneList<HBasicBlock*>* blocks() const { return &blocks_; } 199 const ZoneList<HBasicBlock*>* blocks() const { return &blocks_; }
299 const ZoneList<HPhi*>* phi_list() const { return phi_list_; } 200 const ZoneList<HPhi*>* phi_list() const { return phi_list_; }
300 Handle<String> debug_name() const { return info_->function()->debug_name(); } 201 HBasicBlock* entry_block() const { return entry_block_; }
301 HEnvironment* start_environment() const { return start_environment_; } 202 HEnvironment* start_environment() const { return start_environment_; }
302 203
303 void InitializeInferredTypes(); 204 void InitializeInferredTypes();
304 void InsertTypeConversions(); 205 void InsertTypeConversions();
305 void InsertRepresentationChanges(); 206 void InsertRepresentationChanges();
306 void ComputeMinusZeroChecks(); 207 void ComputeMinusZeroChecks();
307 bool ProcessArgumentsObject(); 208 bool ProcessArgumentsObject();
308 void EliminateRedundantPhis(); 209 void EliminateRedundantPhis();
210 void EliminateUnreachablePhis();
309 void Canonicalize(); 211 void Canonicalize();
310 void OrderBlocks(); 212 void OrderBlocks();
311 void AssignDominators(); 213 void AssignDominators();
312 214
313 // Returns false if there are phi-uses of the arguments-object 215 // Returns false if there are phi-uses of the arguments-object
314 // which are not supported by the optimizing compiler. 216 // which are not supported by the optimizing compiler.
315 bool CollectPhis(); 217 bool CollectPhis();
316 218
317 Handle<Code> Compile(); 219 Handle<Code> Compile(CompilationInfo* info);
318 220
319 void set_undefined_constant(HConstant* constant) { 221 void set_undefined_constant(HConstant* constant) {
320 undefined_constant_.set(constant); 222 undefined_constant_.set(constant);
321 } 223 }
322 HConstant* GetConstantUndefined() const { return undefined_constant_.get(); } 224 HConstant* GetConstantUndefined() const { return undefined_constant_.get(); }
323 HConstant* GetConstant1(); 225 HConstant* GetConstant1();
324 HConstant* GetConstantMinus1(); 226 HConstant* GetConstantMinus1();
325 HConstant* GetConstantTrue(); 227 HConstant* GetConstantTrue();
326 HConstant* GetConstantFalse(); 228 HConstant* GetConstantFalse();
327 229
328 HBasicBlock* CreateBasicBlock(); 230 HBasicBlock* CreateBasicBlock();
329 HArgumentsObject* GetArgumentsObject() const { 231 HArgumentsObject* GetArgumentsObject() const {
330 return arguments_object_.get(); 232 return arguments_object_.get();
331 } 233 }
332 bool HasArgumentsObject() const { return arguments_object_.is_set(); } 234 bool HasArgumentsObject() const { return arguments_object_.is_set(); }
333 235
334 void SetArgumentsObject(HArgumentsObject* object) { 236 void SetArgumentsObject(HArgumentsObject* object) {
335 arguments_object_.set(object); 237 arguments_object_.set(object);
336 } 238 }
337 239
338 // True iff. we are compiling for OSR and the statement is the entry.
339 bool HasOsrEntryAt(IterationStatement* statement);
340
341 int GetMaximumValueID() const { return values_.length(); } 240 int GetMaximumValueID() const { return values_.length(); }
342 int GetNextBlockID() { return next_block_id_++; } 241 int GetNextBlockID() { return next_block_id_++; }
343 int GetNextValueID(HValue* value) { 242 int GetNextValueID(HValue* value) {
344 values_.Add(value); 243 values_.Add(value);
345 return values_.length() - 1; 244 return values_.length() - 1;
346 } 245 }
347 HValue* LookupValue(int id) const { 246 HValue* LookupValue(int id) const {
348 if (id >= 0 && id < values_.length()) return values_[id]; 247 if (id >= 0 && id < values_.length()) return values_[id];
349 return NULL; 248 return NULL;
350 } 249 }
(...skipping 11 matching lines...) Expand all
362 BitVector* visited, 261 BitVector* visited,
363 ZoneList<HBasicBlock*>* order, 262 ZoneList<HBasicBlock*>* order,
364 HBasicBlock* loop_header); 263 HBasicBlock* loop_header);
365 HConstant* GetConstant(SetOncePointer<HConstant>* pointer, 264 HConstant* GetConstant(SetOncePointer<HConstant>* pointer,
366 Object* value); 265 Object* value);
367 266
368 void InsertTypeConversions(HInstruction* instr); 267 void InsertTypeConversions(HInstruction* instr);
369 void PropagateMinusZeroChecks(HValue* value, BitVector* visited); 268 void PropagateMinusZeroChecks(HValue* value, BitVector* visited);
370 void InsertRepresentationChangeForUse(HValue* value, 269 void InsertRepresentationChangeForUse(HValue* value,
371 HValue* use, 270 HValue* use,
372 Representation to, 271 Representation to);
373 bool truncating); 272 void InsertRepresentationChangesForValue(HValue* current,
374 void InsertRepresentationChanges(HValue* current); 273 ZoneList<HValue*>* value_list,
274 ZoneList<Representation>* rep_list);
375 void InferTypes(ZoneList<HValue*>* worklist); 275 void InferTypes(ZoneList<HValue*>* worklist);
376 void InitializeInferredTypes(int from_inclusive, int to_inclusive); 276 void InitializeInferredTypes(int from_inclusive, int to_inclusive);
377 void CheckForBackEdge(HBasicBlock* block, HBasicBlock* successor); 277 void CheckForBackEdge(HBasicBlock* block, HBasicBlock* successor);
378 278
379 int next_block_id_; 279 int next_block_id_;
380 CompilationInfo* info_; 280 HBasicBlock* entry_block_;
381 HEnvironment* start_environment_; 281 HEnvironment* start_environment_;
382 ZoneList<HBasicBlock*> blocks_; 282 ZoneList<HBasicBlock*> blocks_;
383 ZoneList<HValue*> values_; 283 ZoneList<HValue*> values_;
384 ZoneList<HPhi*>* phi_list_; 284 ZoneList<HPhi*>* phi_list_;
385 SetOncePointer<HConstant> undefined_constant_; 285 SetOncePointer<HConstant> undefined_constant_;
386 SetOncePointer<HConstant> constant_1_; 286 SetOncePointer<HConstant> constant_1_;
387 SetOncePointer<HConstant> constant_minus1_; 287 SetOncePointer<HConstant> constant_minus1_;
388 SetOncePointer<HConstant> constant_true_; 288 SetOncePointer<HConstant> constant_true_;
389 SetOncePointer<HConstant> constant_false_; 289 SetOncePointer<HConstant> constant_false_;
390 SetOncePointer<HArgumentsObject> arguments_object_; 290 SetOncePointer<HArgumentsObject> arguments_object_;
391 291
392 friend class HSubgraph;
393
394 DISALLOW_COPY_AND_ASSIGN(HGraph); 292 DISALLOW_COPY_AND_ASSIGN(HGraph);
395 }; 293 };
396 294
397 295
398 class HEnvironment: public ZoneObject { 296 class HEnvironment: public ZoneObject {
399 public: 297 public:
400 HEnvironment(HEnvironment* outer, 298 HEnvironment(HEnvironment* outer,
401 Scope* scope, 299 Scope* scope,
402 Handle<JSFunction> closure); 300 Handle<JSFunction> closure);
403 301
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
474 HEnvironment* CopyForInlining(Handle<JSFunction> target, 372 HEnvironment* CopyForInlining(Handle<JSFunction> target,
475 FunctionLiteral* function, 373 FunctionLiteral* function,
476 bool is_speculative, 374 bool is_speculative,
477 HConstant* undefined) const; 375 HConstant* undefined) const;
478 376
479 void AddIncomingEdge(HBasicBlock* block, HEnvironment* other); 377 void AddIncomingEdge(HBasicBlock* block, HEnvironment* other);
480 378
481 void ClearHistory() { 379 void ClearHistory() {
482 pop_count_ = 0; 380 pop_count_ = 0;
483 push_count_ = 0; 381 push_count_ = 0;
484 assigned_variables_.Clear(); 382 assigned_variables_.Rewind(0);
485 } 383 }
486 384
487 void SetValueAt(int index, HValue* value) { 385 void SetValueAt(int index, HValue* value) {
488 ASSERT(index < length()); 386 ASSERT(index < length());
489 values_[index] = value; 387 values_[index] = value;
490 } 388 }
491 389
492 void PrintTo(StringStream* stream); 390 void PrintTo(StringStream* stream);
493 void PrintToStd(); 391 void PrintToStd();
494 392
(...skipping 26 matching lines...) Expand all
521 int local_count_; 419 int local_count_;
522 HEnvironment* outer_; 420 HEnvironment* outer_;
523 int pop_count_; 421 int pop_count_;
524 int push_count_; 422 int push_count_;
525 int ast_id_; 423 int ast_id_;
526 }; 424 };
527 425
528 426
529 class HGraphBuilder; 427 class HGraphBuilder;
530 428
429 // This class is not BASE_EMBEDDED because our inlining implementation uses
430 // new and delete.
531 class AstContext { 431 class AstContext {
532 public: 432 public:
533 bool IsEffect() const { return kind_ == Expression::kEffect; } 433 bool IsEffect() const { return kind_ == Expression::kEffect; }
534 bool IsValue() const { return kind_ == Expression::kValue; } 434 bool IsValue() const { return kind_ == Expression::kValue; }
535 bool IsTest() const { return kind_ == Expression::kTest; } 435 bool IsTest() const { return kind_ == Expression::kTest; }
536 436
537 // 'Fill' this context with a hydrogen value. The value is assumed to 437 // 'Fill' this context with a hydrogen value. The value is assumed to
538 // have already been inserted in the instruction stream (or not need to 438 // have already been inserted in the instruction stream (or not need to
539 // be, e.g., HPhi). Call this function in tail position in the Visit 439 // be, e.g., HPhi). Call this function in tail position in the Visit
540 // functions for expressions. 440 // functions for expressions.
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after
612 private: 512 private:
613 // Build the shared core part of the translation unpacking a value into 513 // Build the shared core part of the translation unpacking a value into
614 // control flow. 514 // control flow.
615 void BuildBranch(HValue* value); 515 void BuildBranch(HValue* value);
616 516
617 HBasicBlock* if_true_; 517 HBasicBlock* if_true_;
618 HBasicBlock* if_false_; 518 HBasicBlock* if_false_;
619 }; 519 };
620 520
621 521
522 class FunctionState BASE_EMBEDDED {
523 public:
524 FunctionState(HGraphBuilder* owner,
525 CompilationInfo* info,
526 TypeFeedbackOracle* oracle);
527 ~FunctionState();
528
529 CompilationInfo* compilation_info() { return compilation_info_; }
530 TypeFeedbackOracle* oracle() { return oracle_; }
531 AstContext* call_context() { return call_context_; }
532 HBasicBlock* function_return() { return function_return_; }
533 TestContext* test_context() { return test_context_; }
534 void ClearInlinedTestContext() {
535 delete test_context_;
536 test_context_ = NULL;
537 }
538
539 private:
540 HGraphBuilder* owner_;
541
542 CompilationInfo* compilation_info_;
543 TypeFeedbackOracle* oracle_;
544
545 // During function inlining, expression context of the call being
546 // inlined. NULL when not inlining.
547 AstContext* call_context_;
548
549 // When inlining in an effect of value context, this is the return block.
550 // It is NULL otherwise. When inlining in a test context, there are a
551 // pair of return blocks in the context. When not inlining, there is no
552 // local return point.
553 HBasicBlock* function_return_;
554
555 // When inlining a call in a test context, a context containing a pair of
556 // return blocks. NULL in all other cases.
557 TestContext* test_context_;
558
559 FunctionState* outer_;
560 };
561
562
622 class HGraphBuilder: public AstVisitor { 563 class HGraphBuilder: public AstVisitor {
623 public: 564 public:
624 explicit HGraphBuilder(TypeFeedbackOracle* oracle) 565 enum BreakType { BREAK, CONTINUE };
625 : oracle_(oracle), 566
567 // A class encapsulating (lazily-allocated) break and continue blocks for
568 // a breakable statement. Separated from BreakAndContinueScope so that it
569 // can have a separate lifetime.
570 class BreakAndContinueInfo BASE_EMBEDDED {
571 public:
572 explicit BreakAndContinueInfo(BreakableStatement* target)
573 : target_(target), break_block_(NULL), continue_block_(NULL) {
574 }
575
576 BreakableStatement* target() { return target_; }
577 HBasicBlock* break_block() { return break_block_; }
578 void set_break_block(HBasicBlock* block) { break_block_ = block; }
579 HBasicBlock* continue_block() { return continue_block_; }
580 void set_continue_block(HBasicBlock* block) { continue_block_ = block; }
581
582 private:
583 BreakableStatement* target_;
584 HBasicBlock* break_block_;
585 HBasicBlock* continue_block_;
586 };
587
588 // A helper class to maintain a stack of current BreakAndContinueInfo
589 // structures mirroring BreakableStatement nesting.
590 class BreakAndContinueScope BASE_EMBEDDED {
591 public:
592 BreakAndContinueScope(BreakAndContinueInfo* info, HGraphBuilder* owner)
593 : info_(info), owner_(owner), next_(owner->break_scope()) {
594 owner->set_break_scope(this);
595 }
596
597 ~BreakAndContinueScope() { owner_->set_break_scope(next_); }
598
599 BreakAndContinueInfo* info() { return info_; }
600 HGraphBuilder* owner() { return owner_; }
601 BreakAndContinueScope* next() { return next_; }
602
603 // Search the break stack for a break or continue target.
604 HBasicBlock* Get(BreakableStatement* stmt, BreakType type);
605
606 private:
607 BreakAndContinueInfo* info_;
608 HGraphBuilder* owner_;
609 BreakAndContinueScope* next_;
610 };
611
612 HGraphBuilder(CompilationInfo* info, TypeFeedbackOracle* oracle)
613 : function_state_(NULL),
614 initial_function_state_(this, info, oracle),
615 ast_context_(NULL),
616 break_scope_(NULL),
626 graph_(NULL), 617 graph_(NULL),
627 current_subgraph_(NULL), 618 current_block_(NULL),
628 peeled_statement_(NULL), 619 inlined_count_(0) {
629 ast_context_(NULL), 620 // This is not initialized in the initializer list because the
630 call_context_(NULL), 621 // constructor for the initial state relies on function_state_ == NULL
631 function_return_(NULL), 622 // to know it's the initial state.
632 inlined_count_(0) { } 623 function_state_= &initial_function_state_;
624 }
633 625
634 HGraph* CreateGraph(CompilationInfo* info); 626 HGraph* CreateGraph();
635 627
636 // Simple accessors. 628 // Simple accessors.
637 HGraph* graph() const { return graph_; } 629 HGraph* graph() const { return graph_; }
638 HSubgraph* subgraph() const { return current_subgraph_; } 630 BreakAndContinueScope* break_scope() const { return break_scope_; }
631 void set_break_scope(BreakAndContinueScope* head) { break_scope_ = head; }
639 632
640 HEnvironment* environment() const { return subgraph()->environment(); } 633 HBasicBlock* current_block() const { return current_block_; }
641 HBasicBlock* CurrentBlock() const { return subgraph()->exit_block(); } 634 void set_current_block(HBasicBlock* block) { current_block_ = block; }
635 HEnvironment* environment() const {
636 return current_block()->last_environment();
637 }
642 638
643 // Adding instructions. 639 // Adding instructions.
644 HInstruction* AddInstruction(HInstruction* instr); 640 HInstruction* AddInstruction(HInstruction* instr);
645 void AddSimulate(int id); 641 void AddSimulate(int id);
646 642
647 // Bailout environment manipulation. 643 // Bailout environment manipulation.
648 void Push(HValue* value) { environment()->Push(value); } 644 void Push(HValue* value) { environment()->Push(value); }
649 HValue* Pop() { return environment()->Pop(); } 645 HValue* Pop() { return environment()->Pop(); }
650 646
651 private: 647 private:
652 // Type of a member function that generates inline code for a native function. 648 // Type of a member function that generates inline code for a native function.
653 typedef void (HGraphBuilder::*InlineFunctionGenerator)(int argument_count, 649 typedef void (HGraphBuilder::*InlineFunctionGenerator)(CallRuntime* call);
654 int ast_id);
655 650
656 // Forward declarations for inner scope classes. 651 // Forward declarations for inner scope classes.
657 class SubgraphScope; 652 class SubgraphScope;
658 653
659 static const InlineFunctionGenerator kInlineFunctionGenerators[]; 654 static const InlineFunctionGenerator kInlineFunctionGenerators[];
660 655
661 static const int kMaxCallPolymorphism = 4; 656 static const int kMaxCallPolymorphism = 4;
662 static const int kMaxLoadPolymorphism = 4; 657 static const int kMaxLoadPolymorphism = 4;
663 static const int kMaxStorePolymorphism = 4; 658 static const int kMaxStorePolymorphism = 4;
664 659
665 static const int kMaxInlinedNodes = 196; 660 static const int kMaxInlinedNodes = 196;
666 static const int kMaxInlinedSize = 196; 661 static const int kMaxInlinedSize = 196;
667 static const int kMaxSourceSize = 600; 662 static const int kMaxSourceSize = 600;
668 663
669 // Simple accessors. 664 // Simple accessors.
670 TypeFeedbackOracle* oracle() const { return oracle_; } 665 FunctionState* function_state() const { return function_state_; }
666 void set_function_state(FunctionState* state) { function_state_ = state; }
667
671 AstContext* ast_context() const { return ast_context_; } 668 AstContext* ast_context() const { return ast_context_; }
672 void set_ast_context(AstContext* context) { ast_context_ = context; } 669 void set_ast_context(AstContext* context) { ast_context_ = context; }
673 AstContext* call_context() const { return call_context_; } 670
674 HBasicBlock* function_return() const { return function_return_; } 671 // Accessors forwarded to the function state.
672 CompilationInfo* info() const {
673 return function_state()->compilation_info();
674 }
675 TypeFeedbackOracle* oracle() const { return function_state()->oracle(); }
676
677 AstContext* call_context() const {
678 return function_state()->call_context();
679 }
680 HBasicBlock* function_return() const {
681 return function_state()->function_return();
682 }
683 TestContext* inlined_test_context() const {
684 return function_state()->test_context();
685 }
686 void ClearInlinedTestContext() {
687 function_state()->ClearInlinedTestContext();
688 }
675 689
676 // Generators for inline runtime functions. 690 // Generators for inline runtime functions.
677 #define INLINE_FUNCTION_GENERATOR_DECLARATION(Name, argc, ressize) \ 691 #define INLINE_FUNCTION_GENERATOR_DECLARATION(Name, argc, ressize) \
678 void Generate##Name(int argument_count, int ast_id); 692 void Generate##Name(CallRuntime* call);
679 693
680 INLINE_FUNCTION_LIST(INLINE_FUNCTION_GENERATOR_DECLARATION) 694 INLINE_FUNCTION_LIST(INLINE_FUNCTION_GENERATOR_DECLARATION)
681 INLINE_RUNTIME_FUNCTION_LIST(INLINE_FUNCTION_GENERATOR_DECLARATION) 695 INLINE_RUNTIME_FUNCTION_LIST(INLINE_FUNCTION_GENERATOR_DECLARATION)
682 #undef INLINE_FUNCTION_GENERATOR_DECLARATION 696 #undef INLINE_FUNCTION_GENERATOR_DECLARATION
683 697
684 void Bailout(const char* reason); 698 void Bailout(const char* reason);
685 699
686 void AppendPeeledWhile(IterationStatement* stmt, 700 void PreProcessOsrEntry(IterationStatement* statement);
687 HSubgraph* cond_graph, 701 // True iff. we are compiling for OSR and the statement is the entry.
688 HSubgraph* body_graph, 702 bool HasOsrEntryAt(IterationStatement* statement);
689 HSubgraph* exit_graph);
690 703
691 void AddToSubgraph(HSubgraph* graph, ZoneList<Statement*>* stmts); 704 HBasicBlock* CreateJoin(HBasicBlock* first,
692 void AddToSubgraph(HSubgraph* graph, Statement* stmt); 705 HBasicBlock* second,
693 void AddToSubgraph(HSubgraph* graph, Expression* expr); 706 int join_id);
707
708 // Create a back edge in the flow graph. body_exit is the predecessor
709 // block and loop_entry is the successor block. loop_successor is the
710 // block where control flow exits the loop normally (e.g., via failure of
711 // the condition) and break_block is the block where control flow breaks
712 // from the loop. All blocks except loop_entry can be NULL. The return
713 // value is the new successor block which is the join of loop_successor
714 // and break_block, or NULL.
715 HBasicBlock* CreateLoop(IterationStatement* statement,
716 HBasicBlock* loop_entry,
717 HBasicBlock* body_exit,
718 HBasicBlock* loop_successor,
719 HBasicBlock* break_block);
720
721 HBasicBlock* JoinContinue(IterationStatement* statement,
722 HBasicBlock* exit_block,
723 HBasicBlock* continue_block);
694 724
695 HValue* Top() const { return environment()->Top(); } 725 HValue* Top() const { return environment()->Top(); }
696 void Drop(int n) { environment()->Drop(n); } 726 void Drop(int n) { environment()->Drop(n); }
697 void Bind(Variable* var, HValue* value) { environment()->Bind(var, value); } 727 void Bind(Variable* var, HValue* value) { environment()->Bind(var, value); }
698 728
699 void VisitForValue(Expression* expr); 729 void VisitForValue(Expression* expr);
700 void VisitForEffect(Expression* expr); 730 void VisitForEffect(Expression* expr);
701 void VisitForControl(Expression* expr, 731 void VisitForControl(Expression* expr,
702 HBasicBlock* true_block, 732 HBasicBlock* true_block,
703 HBasicBlock* false_block); 733 HBasicBlock* false_block);
704 734
705 // Visit an argument subexpression. 735 // Visit an argument subexpression and emit a push to the outgoing
736 // arguments.
706 void VisitArgument(Expression* expr); 737 void VisitArgument(Expression* expr);
707 void VisitArgumentList(ZoneList<Expression*>* arguments); 738 void VisitArgumentList(ZoneList<Expression*>* arguments);
708 739
740 // Visit a list of expressions from left to right, each in a value context.
741 void VisitExpressions(ZoneList<Expression*>* exprs);
742
709 void AddPhi(HPhi* phi); 743 void AddPhi(HPhi* phi);
710 744
711 void PushAndAdd(HInstruction* instr); 745 void PushAndAdd(HInstruction* instr);
712 746
713 // Remove the arguments from the bailout environment and emit instructions 747 // Remove the arguments from the bailout environment and emit instructions
714 // to push them as outgoing parameters. 748 // to push them as outgoing parameters.
715 void PreProcessCall(HCall* call); 749 template <int V> HInstruction* PreProcessCall(HCall<V>* call);
716 750
717 void AssumeRepresentation(HValue* value, Representation r); 751 void AssumeRepresentation(HValue* value, Representation r);
718 static Representation ToRepresentation(TypeInfo info); 752 static Representation ToRepresentation(TypeInfo info);
719 753
720 void SetupScope(Scope* scope); 754 void SetupScope(Scope* scope);
721 virtual void VisitStatements(ZoneList<Statement*>* statements); 755 virtual void VisitStatements(ZoneList<Statement*>* statements);
722 756
723 #define DECLARE_VISIT(type) virtual void Visit##type(type* node); 757 #define DECLARE_VISIT(type) virtual void Visit##type(type* node);
724 AST_NODE_LIST(DECLARE_VISIT) 758 AST_NODE_LIST(DECLARE_VISIT)
725 #undef DECLARE_VISIT 759 #undef DECLARE_VISIT
726 760
727 bool ShouldPeel(HSubgraph* cond, HSubgraph* body);
728
729 HBasicBlock* CreateBasicBlock(HEnvironment* env); 761 HBasicBlock* CreateBasicBlock(HEnvironment* env);
730 HSubgraph* CreateEmptySubgraph(); 762 HBasicBlock* CreateLoopHeaderBlock();
731 HSubgraph* CreateGotoSubgraph(HEnvironment* env);
732 HSubgraph* CreateBranchSubgraph(HEnvironment* env);
733 HSubgraph* CreateLoopHeaderSubgraph(HEnvironment* env);
734 HSubgraph* CreateInlinedSubgraph(HEnvironment* outer,
735 Handle<JSFunction> target,
736 FunctionLiteral* function);
737 763
738 // Helpers for flow graph construction. 764 // Helpers for flow graph construction.
739 void LookupGlobalPropertyCell(Variable* var, 765 void LookupGlobalPropertyCell(Variable* var,
740 LookupResult* lookup, 766 LookupResult* lookup,
741 bool is_store); 767 bool is_store);
742 768
743 bool TryArgumentsAccess(Property* expr); 769 bool TryArgumentsAccess(Property* expr);
744 bool TryCallApply(Call* expr); 770 bool TryCallApply(Call* expr);
745 bool TryInline(Call* expr); 771 bool TryInline(Call* expr);
746 bool TryInlineBuiltinFunction(Call* expr, 772 bool TryInlineBuiltinFunction(Call* expr,
747 HValue* receiver, 773 HValue* receiver,
748 Handle<Map> receiver_map, 774 Handle<Map> receiver_map,
749 CheckType check_type); 775 CheckType check_type);
750 void TraceInline(Handle<JSFunction> target, bool result); 776
777 // If --trace-inlining, print a line of the inlining trace. Inlining
778 // succeeded if the reason string is NULL and failed if there is a
779 // non-NULL reason string.
780 void TraceInline(Handle<JSFunction> target, const char* failure_reason);
751 781
752 void HandleGlobalVariableAssignment(Variable* var, 782 void HandleGlobalVariableAssignment(Variable* var,
753 HValue* value, 783 HValue* value,
754 int position, 784 int position,
755 int ast_id); 785 int ast_id);
756 786
757 void HandlePropertyAssignment(Assignment* expr); 787 void HandlePropertyAssignment(Assignment* expr);
758 void HandleCompoundAssignment(Assignment* expr); 788 void HandleCompoundAssignment(Assignment* expr);
759 void HandlePolymorphicLoadNamedField(Property* expr, 789 void HandlePolymorphicLoadNamedField(Property* expr,
760 HValue* object, 790 HValue* object,
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
809 HValue* value); 839 HValue* value);
810 HInstruction* BuildStoreKeyedGeneric(HValue* object, 840 HInstruction* BuildStoreKeyedGeneric(HValue* object,
811 HValue* key, 841 HValue* key,
812 HValue* value); 842 HValue* value);
813 843
814 HInstruction* BuildStoreKeyedFastElement(HValue* object, 844 HInstruction* BuildStoreKeyedFastElement(HValue* object,
815 HValue* key, 845 HValue* key,
816 HValue* val, 846 HValue* val,
817 Expression* expr); 847 Expression* expr);
818 848
819 HCompare* BuildSwitchCompare(HSubgraph* subgraph, 849 HInstruction* BuildStoreKeyedPixelArrayElement(HValue* object,
820 HValue* switch_value, 850 HValue* key,
821 CaseClause* clause); 851 HValue* val,
852 Expression* expr);
822 853
823 HValue* BuildContextChainWalk(Variable* var); 854 HValue* BuildContextChainWalk(Variable* var);
824 855
825 void AddCheckConstantFunction(Call* expr, 856 void AddCheckConstantFunction(Call* expr,
826 HValue* receiver, 857 HValue* receiver,
827 Handle<Map> receiver_map, 858 Handle<Map> receiver_map,
828 bool smi_and_map_check); 859 bool smi_and_map_check);
829 860
830 861
831 HBasicBlock* BuildTypeSwitch(HValue* receiver, 862 // The translation state of the currently-being-translated function.
832 ZoneMapList* maps, 863 FunctionState* function_state_;
833 ZoneList<HSubgraph*>* body_graphs,
834 HSubgraph* default_graph,
835 int join_id);
836 864
837 TypeFeedbackOracle* oracle_; 865 // The base of the function state stack.
838 HGraph* graph_; 866 FunctionState initial_function_state_;
839 HSubgraph* current_subgraph_; 867
840 IterationStatement* peeled_statement_;
841 // Expression context of the currently visited subexpression. NULL when 868 // Expression context of the currently visited subexpression. NULL when
842 // visiting statements. 869 // visiting statements.
843 AstContext* ast_context_; 870 AstContext* ast_context_;
844 871
845 // During function inlining, expression context of the call being 872 // A stack of breakable statements entered.
846 // inlined. NULL when not inlining. 873 BreakAndContinueScope* break_scope_;
847 AstContext* call_context_;
848 874
849 // When inlining a call in an effect or value context, the return 875 HGraph* graph_;
850 // block. NULL otherwise. When inlining a call in a test context, there 876 HBasicBlock* current_block_;
851 // are a pair of target blocks in the call context.
852 HBasicBlock* function_return_;
853 877
854 int inlined_count_; 878 int inlined_count_;
855 879
880 friend class FunctionState; // Pushes and pops the state stack.
856 friend class AstContext; // Pushes and pops the AST context stack. 881 friend class AstContext; // Pushes and pops the AST context stack.
857 882
858 DISALLOW_COPY_AND_ASSIGN(HGraphBuilder); 883 DISALLOW_COPY_AND_ASSIGN(HGraphBuilder);
859 }; 884 };
860 885
861 886
862 class HValueMap: public ZoneObject { 887 class HValueMap: public ZoneObject {
863 public: 888 public:
864 HValueMap() 889 HValueMap()
865 : array_size_(0), 890 : array_size_(0),
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
907 int present_flags_; // All flags that are in any value in the HValueMap. 932 int present_flags_; // All flags that are in any value in the HValueMap.
908 HValueMapListElement* array_; // Primary store - contains the first value 933 HValueMapListElement* array_; // Primary store - contains the first value
909 // with a given hash. Colliding elements are stored in linked lists. 934 // with a given hash. Colliding elements are stored in linked lists.
910 HValueMapListElement* lists_; // The linked lists containing hash collisions. 935 HValueMapListElement* lists_; // The linked lists containing hash collisions.
911 int free_list_head_; // Unused elements in lists_ are on the free list. 936 int free_list_head_; // Unused elements in lists_ are on the free list.
912 }; 937 };
913 938
914 939
915 class HStatistics: public Malloced { 940 class HStatistics: public Malloced {
916 public: 941 public:
942 void Initialize(CompilationInfo* info);
917 void Print(); 943 void Print();
918 void SaveTiming(const char* name, int64_t ticks, unsigned size); 944 void SaveTiming(const char* name, int64_t ticks, unsigned size);
919 static HStatistics* Instance() { 945 static HStatistics* Instance() {
920 static SetOncePointer<HStatistics> instance; 946 static SetOncePointer<HStatistics> instance;
921 if (!instance.is_set()) { 947 if (!instance.is_set()) {
922 instance.set(new HStatistics()); 948 instance.set(new HStatistics());
923 } 949 }
924 return instance.get(); 950 return instance.get();
925 } 951 }
926 952
927 private: 953 private:
928 954
929 HStatistics() 955 HStatistics()
930 : timing_(5), 956 : timing_(5),
931 names_(5), 957 names_(5),
932 sizes_(5), 958 sizes_(5),
933 total_(0), 959 total_(0),
934 total_size_(0), 960 total_size_(0),
935 full_code_gen_(0) { } 961 full_code_gen_(0),
962 source_size_(0) { }
936 963
937 List<int64_t> timing_; 964 List<int64_t> timing_;
938 List<const char*> names_; 965 List<const char*> names_;
939 List<unsigned> sizes_; 966 List<unsigned> sizes_;
940 int64_t total_; 967 int64_t total_;
941 unsigned total_size_; 968 unsigned total_size_;
942 int64_t full_code_gen_; 969 int64_t full_code_gen_;
970 double source_size_;
943 }; 971 };
944 972
945 973
946 class HPhase BASE_EMBEDDED { 974 class HPhase BASE_EMBEDDED {
947 public: 975 public:
948 static const char* const kFullCodeGen; 976 static const char* const kFullCodeGen;
949 static const char* const kTotal; 977 static const char* const kTotal;
950 978
951 explicit HPhase(const char* name) { Begin(name, NULL, NULL, NULL); } 979 explicit HPhase(const char* name) { Begin(name, NULL, NULL, NULL); }
952 HPhase(const char* name, HGraph* graph) { 980 HPhase(const char* name, HGraph* graph) {
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after
1066 const char* filename_; 1094 const char* filename_;
1067 HeapStringAllocator string_allocator_; 1095 HeapStringAllocator string_allocator_;
1068 StringStream trace_; 1096 StringStream trace_;
1069 int indent_; 1097 int indent_;
1070 }; 1098 };
1071 1099
1072 1100
1073 } } // namespace v8::internal 1101 } } // namespace v8::internal
1074 1102
1075 #endif // V8_HYDROGEN_H_ 1103 #endif // V8_HYDROGEN_H_
OLDNEW
« no previous file with comments | « src/heap-profiler.cc ('k') | src/hydrogen.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698