OLD | NEW |
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 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
188 | 188 |
189 class AstNode: public ZoneObject { | 189 class AstNode: public ZoneObject { |
190 public: | 190 public: |
191 #define DECLARE_TYPE_ENUM(type) k##type, | 191 #define DECLARE_TYPE_ENUM(type) k##type, |
192 enum Type { | 192 enum Type { |
193 AST_NODE_LIST(DECLARE_TYPE_ENUM) | 193 AST_NODE_LIST(DECLARE_TYPE_ENUM) |
194 kInvalid = -1 | 194 kInvalid = -1 |
195 }; | 195 }; |
196 #undef DECLARE_TYPE_ENUM | 196 #undef DECLARE_TYPE_ENUM |
197 | 197 |
198 static const int kNoNumber = -1; | |
199 static const int kFunctionEntryId = 2; // Using 0 could disguise errors. | |
200 // This AST id identifies the point after the declarations have been | |
201 // visited. We need it to capture the environment effects of declarations | |
202 // that emit code (function declarations). | |
203 static const int kDeclarationsId = 3; | |
204 | |
205 void* operator new(size_t size, Zone* zone) { | 198 void* operator new(size_t size, Zone* zone) { |
206 return zone->New(static_cast<int>(size)); | 199 return zone->New(static_cast<int>(size)); |
207 } | 200 } |
208 | 201 |
209 AstNode() { } | 202 AstNode() { } |
210 | 203 |
211 virtual ~AstNode() { } | 204 virtual ~AstNode() { } |
212 | 205 |
213 virtual void Accept(AstVisitor* v) = 0; | 206 virtual void Accept(AstVisitor* v) = 0; |
214 virtual Type node_type() const = 0; | 207 virtual Type node_type() const = 0; |
(...skipping 14 matching lines...) Expand all Loading... |
229 static int GetNextId(Isolate* isolate) { | 222 static int GetNextId(Isolate* isolate) { |
230 return ReserveIdRange(isolate, 1); | 223 return ReserveIdRange(isolate, 1); |
231 } | 224 } |
232 | 225 |
233 static int ReserveIdRange(Isolate* isolate, int n) { | 226 static int ReserveIdRange(Isolate* isolate, int n) { |
234 int tmp = isolate->ast_node_id(); | 227 int tmp = isolate->ast_node_id(); |
235 isolate->set_ast_node_id(tmp + n); | 228 isolate->set_ast_node_id(tmp + n); |
236 return tmp; | 229 return tmp; |
237 } | 230 } |
238 | 231 |
| 232 // Some nodes re-use bailout IDs for type feedback. |
| 233 static TypeFeedbackId reuse(BailoutId id) { |
| 234 return TypeFeedbackId(id.ToInt()); |
| 235 } |
| 236 |
| 237 |
239 private: | 238 private: |
240 // Hidden to prevent accidental usage. It would have to load the | 239 // Hidden to prevent accidental usage. It would have to load the |
241 // current zone from the TLS. | 240 // current zone from the TLS. |
242 void* operator new(size_t size); | 241 void* operator new(size_t size); |
243 | 242 |
244 friend class CaseClause; // Generates AST IDs. | 243 friend class CaseClause; // Generates AST IDs. |
245 }; | 244 }; |
246 | 245 |
247 | 246 |
248 class Statement: public AstNode { | 247 class Statement: public AstNode { |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
342 UNREACHABLE(); | 341 UNREACHABLE(); |
343 return NULL; | 342 return NULL; |
344 } | 343 } |
345 Handle<Map> GetMonomorphicReceiverType() { | 344 Handle<Map> GetMonomorphicReceiverType() { |
346 ASSERT(IsMonomorphic()); | 345 ASSERT(IsMonomorphic()); |
347 SmallMapList* types = GetReceiverTypes(); | 346 SmallMapList* types = GetReceiverTypes(); |
348 ASSERT(types != NULL && types->length() == 1); | 347 ASSERT(types != NULL && types->length() == 1); |
349 return types->at(0); | 348 return types->at(0); |
350 } | 349 } |
351 | 350 |
352 unsigned id() const { return id_; } | 351 BailoutId id() const { return id_; } |
353 unsigned test_id() const { return test_id_; } | 352 TypeFeedbackId test_id() const { return test_id_; } |
354 | 353 |
355 protected: | 354 protected: |
356 explicit Expression(Isolate* isolate) | 355 explicit Expression(Isolate* isolate) |
357 : id_(GetNextId(isolate)), | 356 : id_(GetNextId(isolate)), |
358 test_id_(GetNextId(isolate)) {} | 357 test_id_(GetNextId(isolate)) {} |
359 | 358 |
360 private: | 359 private: |
361 const int id_; | 360 const BailoutId id_; |
362 const int test_id_; | 361 const TypeFeedbackId test_id_; |
363 }; | 362 }; |
364 | 363 |
365 | 364 |
366 class BreakableStatement: public Statement { | 365 class BreakableStatement: public Statement { |
367 public: | 366 public: |
368 enum Type { | 367 enum Type { |
369 TARGET_FOR_ANONYMOUS, | 368 TARGET_FOR_ANONYMOUS, |
370 TARGET_FOR_NAMED_ONLY | 369 TARGET_FOR_NAMED_ONLY |
371 }; | 370 }; |
372 | 371 |
373 // The labels associated with this statement. May be NULL; | 372 // The labels associated with this statement. May be NULL; |
374 // if it is != NULL, guaranteed to contain at least one entry. | 373 // if it is != NULL, guaranteed to contain at least one entry. |
375 ZoneStringList* labels() const { return labels_; } | 374 ZoneStringList* labels() const { return labels_; } |
376 | 375 |
377 // Type testing & conversion. | 376 // Type testing & conversion. |
378 virtual BreakableStatement* AsBreakableStatement() { return this; } | 377 virtual BreakableStatement* AsBreakableStatement() { return this; } |
379 | 378 |
380 // Code generation | 379 // Code generation |
381 Label* break_target() { return &break_target_; } | 380 Label* break_target() { return &break_target_; } |
382 | 381 |
383 // Testers. | 382 // Testers. |
384 bool is_target_for_anonymous() const { return type_ == TARGET_FOR_ANONYMOUS; } | 383 bool is_target_for_anonymous() const { return type_ == TARGET_FOR_ANONYMOUS; } |
385 | 384 |
386 // Bailout support. | 385 BailoutId EntryId() const { return entry_id_; } |
387 int EntryId() const { return entry_id_; } | 386 BailoutId ExitId() const { return exit_id_; } |
388 int ExitId() const { return exit_id_; } | |
389 | 387 |
390 protected: | 388 protected: |
391 BreakableStatement(Isolate* isolate, ZoneStringList* labels, Type type) | 389 BreakableStatement(Isolate* isolate, ZoneStringList* labels, Type type) |
392 : labels_(labels), | 390 : labels_(labels), |
393 type_(type), | 391 type_(type), |
394 entry_id_(GetNextId(isolate)), | 392 entry_id_(GetNextId(isolate)), |
395 exit_id_(GetNextId(isolate)) { | 393 exit_id_(GetNextId(isolate)) { |
396 ASSERT(labels == NULL || labels->length() > 0); | 394 ASSERT(labels == NULL || labels->length() > 0); |
397 } | 395 } |
398 | 396 |
399 | 397 |
400 private: | 398 private: |
401 ZoneStringList* labels_; | 399 ZoneStringList* labels_; |
402 Type type_; | 400 Type type_; |
403 Label break_target_; | 401 Label break_target_; |
404 const int entry_id_; | 402 const BailoutId entry_id_; |
405 const int exit_id_; | 403 const BailoutId exit_id_; |
406 }; | 404 }; |
407 | 405 |
408 | 406 |
409 class Block: public BreakableStatement { | 407 class Block: public BreakableStatement { |
410 public: | 408 public: |
411 DECLARE_NODE_TYPE(Block) | 409 DECLARE_NODE_TYPE(Block) |
412 | 410 |
413 void AddStatement(Statement* statement, Zone* zone) { | 411 void AddStatement(Statement* statement, Zone* zone) { |
414 statements_.Add(statement, zone); | 412 statements_.Add(statement, zone); |
415 } | 413 } |
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
669 }; | 667 }; |
670 | 668 |
671 | 669 |
672 class IterationStatement: public BreakableStatement { | 670 class IterationStatement: public BreakableStatement { |
673 public: | 671 public: |
674 // Type testing & conversion. | 672 // Type testing & conversion. |
675 virtual IterationStatement* AsIterationStatement() { return this; } | 673 virtual IterationStatement* AsIterationStatement() { return this; } |
676 | 674 |
677 Statement* body() const { return body_; } | 675 Statement* body() const { return body_; } |
678 | 676 |
679 // Bailout support. | 677 BailoutId OsrEntryId() const { return osr_entry_id_; } |
680 int OsrEntryId() const { return osr_entry_id_; } | 678 virtual BailoutId ContinueId() const = 0; |
681 virtual int ContinueId() const = 0; | 679 virtual BailoutId StackCheckId() const = 0; |
682 virtual int StackCheckId() const = 0; | |
683 | 680 |
684 // Code generation | 681 // Code generation |
685 Label* continue_target() { return &continue_target_; } | 682 Label* continue_target() { return &continue_target_; } |
686 | 683 |
687 protected: | 684 protected: |
688 IterationStatement(Isolate* isolate, ZoneStringList* labels) | 685 IterationStatement(Isolate* isolate, ZoneStringList* labels) |
689 : BreakableStatement(isolate, labels, TARGET_FOR_ANONYMOUS), | 686 : BreakableStatement(isolate, labels, TARGET_FOR_ANONYMOUS), |
690 body_(NULL), | 687 body_(NULL), |
691 osr_entry_id_(GetNextId(isolate)) { | 688 osr_entry_id_(GetNextId(isolate)) { |
692 } | 689 } |
693 | 690 |
694 void Initialize(Statement* body) { | 691 void Initialize(Statement* body) { |
695 body_ = body; | 692 body_ = body; |
696 } | 693 } |
697 | 694 |
698 private: | 695 private: |
699 Statement* body_; | 696 Statement* body_; |
700 Label continue_target_; | 697 Label continue_target_; |
701 const int osr_entry_id_; | 698 const BailoutId osr_entry_id_; |
702 }; | 699 }; |
703 | 700 |
704 | 701 |
705 class DoWhileStatement: public IterationStatement { | 702 class DoWhileStatement: public IterationStatement { |
706 public: | 703 public: |
707 DECLARE_NODE_TYPE(DoWhileStatement) | 704 DECLARE_NODE_TYPE(DoWhileStatement) |
708 | 705 |
709 void Initialize(Expression* cond, Statement* body) { | 706 void Initialize(Expression* cond, Statement* body) { |
710 IterationStatement::Initialize(body); | 707 IterationStatement::Initialize(body); |
711 cond_ = cond; | 708 cond_ = cond; |
712 } | 709 } |
713 | 710 |
714 Expression* cond() const { return cond_; } | 711 Expression* cond() const { return cond_; } |
715 | 712 |
716 // Position where condition expression starts. We need it to make | 713 // Position where condition expression starts. We need it to make |
717 // the loop's condition a breakable location. | 714 // the loop's condition a breakable location. |
718 int condition_position() { return condition_position_; } | 715 int condition_position() { return condition_position_; } |
719 void set_condition_position(int pos) { condition_position_ = pos; } | 716 void set_condition_position(int pos) { condition_position_ = pos; } |
720 | 717 |
721 // Bailout support. | 718 virtual BailoutId ContinueId() const { return continue_id_; } |
722 virtual int ContinueId() const { return continue_id_; } | 719 virtual BailoutId StackCheckId() const { return back_edge_id_; } |
723 virtual int StackCheckId() const { return back_edge_id_; } | 720 BailoutId BackEdgeId() const { return back_edge_id_; } |
724 int BackEdgeId() const { return back_edge_id_; } | |
725 | 721 |
726 protected: | 722 protected: |
727 template<class> friend class AstNodeFactory; | 723 template<class> friend class AstNodeFactory; |
728 | 724 |
729 DoWhileStatement(Isolate* isolate, ZoneStringList* labels) | 725 DoWhileStatement(Isolate* isolate, ZoneStringList* labels) |
730 : IterationStatement(isolate, labels), | 726 : IterationStatement(isolate, labels), |
731 cond_(NULL), | 727 cond_(NULL), |
732 condition_position_(-1), | 728 condition_position_(-1), |
733 continue_id_(GetNextId(isolate)), | 729 continue_id_(GetNextId(isolate)), |
734 back_edge_id_(GetNextId(isolate)) { | 730 back_edge_id_(GetNextId(isolate)) { |
735 } | 731 } |
736 | 732 |
737 private: | 733 private: |
738 Expression* cond_; | 734 Expression* cond_; |
739 int condition_position_; | 735 int condition_position_; |
740 const int continue_id_; | 736 const BailoutId continue_id_; |
741 const int back_edge_id_; | 737 const BailoutId back_edge_id_; |
742 }; | 738 }; |
743 | 739 |
744 | 740 |
745 class WhileStatement: public IterationStatement { | 741 class WhileStatement: public IterationStatement { |
746 public: | 742 public: |
747 DECLARE_NODE_TYPE(WhileStatement) | 743 DECLARE_NODE_TYPE(WhileStatement) |
748 | 744 |
749 void Initialize(Expression* cond, Statement* body) { | 745 void Initialize(Expression* cond, Statement* body) { |
750 IterationStatement::Initialize(body); | 746 IterationStatement::Initialize(body); |
751 cond_ = cond; | 747 cond_ = cond; |
752 } | 748 } |
753 | 749 |
754 Expression* cond() const { return cond_; } | 750 Expression* cond() const { return cond_; } |
755 bool may_have_function_literal() const { | 751 bool may_have_function_literal() const { |
756 return may_have_function_literal_; | 752 return may_have_function_literal_; |
757 } | 753 } |
758 void set_may_have_function_literal(bool value) { | 754 void set_may_have_function_literal(bool value) { |
759 may_have_function_literal_ = value; | 755 may_have_function_literal_ = value; |
760 } | 756 } |
761 | 757 |
762 // Bailout support. | 758 virtual BailoutId ContinueId() const { return EntryId(); } |
763 virtual int ContinueId() const { return EntryId(); } | 759 virtual BailoutId StackCheckId() const { return body_id_; } |
764 virtual int StackCheckId() const { return body_id_; } | 760 BailoutId BodyId() const { return body_id_; } |
765 int BodyId() const { return body_id_; } | |
766 | 761 |
767 protected: | 762 protected: |
768 template<class> friend class AstNodeFactory; | 763 template<class> friend class AstNodeFactory; |
769 | 764 |
770 WhileStatement(Isolate* isolate, ZoneStringList* labels) | 765 WhileStatement(Isolate* isolate, ZoneStringList* labels) |
771 : IterationStatement(isolate, labels), | 766 : IterationStatement(isolate, labels), |
772 cond_(NULL), | 767 cond_(NULL), |
773 may_have_function_literal_(true), | 768 may_have_function_literal_(true), |
774 body_id_(GetNextId(isolate)) { | 769 body_id_(GetNextId(isolate)) { |
775 } | 770 } |
776 | 771 |
777 private: | 772 private: |
778 Expression* cond_; | 773 Expression* cond_; |
779 // True if there is a function literal subexpression in the condition. | 774 // True if there is a function literal subexpression in the condition. |
780 bool may_have_function_literal_; | 775 bool may_have_function_literal_; |
781 const int body_id_; | 776 const BailoutId body_id_; |
782 }; | 777 }; |
783 | 778 |
784 | 779 |
785 class ForStatement: public IterationStatement { | 780 class ForStatement: public IterationStatement { |
786 public: | 781 public: |
787 DECLARE_NODE_TYPE(ForStatement) | 782 DECLARE_NODE_TYPE(ForStatement) |
788 | 783 |
789 void Initialize(Statement* init, | 784 void Initialize(Statement* init, |
790 Expression* cond, | 785 Expression* cond, |
791 Statement* next, | 786 Statement* next, |
792 Statement* body) { | 787 Statement* body) { |
793 IterationStatement::Initialize(body); | 788 IterationStatement::Initialize(body); |
794 init_ = init; | 789 init_ = init; |
795 cond_ = cond; | 790 cond_ = cond; |
796 next_ = next; | 791 next_ = next; |
797 } | 792 } |
798 | 793 |
799 Statement* init() const { return init_; } | 794 Statement* init() const { return init_; } |
800 Expression* cond() const { return cond_; } | 795 Expression* cond() const { return cond_; } |
801 Statement* next() const { return next_; } | 796 Statement* next() const { return next_; } |
802 | 797 |
803 bool may_have_function_literal() const { | 798 bool may_have_function_literal() const { |
804 return may_have_function_literal_; | 799 return may_have_function_literal_; |
805 } | 800 } |
806 void set_may_have_function_literal(bool value) { | 801 void set_may_have_function_literal(bool value) { |
807 may_have_function_literal_ = value; | 802 may_have_function_literal_ = value; |
808 } | 803 } |
809 | 804 |
810 // Bailout support. | 805 virtual BailoutId ContinueId() const { return continue_id_; } |
811 virtual int ContinueId() const { return continue_id_; } | 806 virtual BailoutId StackCheckId() const { return body_id_; } |
812 virtual int StackCheckId() const { return body_id_; } | 807 BailoutId BodyId() const { return body_id_; } |
813 int BodyId() const { return body_id_; } | |
814 | 808 |
815 bool is_fast_smi_loop() { return loop_variable_ != NULL; } | 809 bool is_fast_smi_loop() { return loop_variable_ != NULL; } |
816 Variable* loop_variable() { return loop_variable_; } | 810 Variable* loop_variable() { return loop_variable_; } |
817 void set_loop_variable(Variable* var) { loop_variable_ = var; } | 811 void set_loop_variable(Variable* var) { loop_variable_ = var; } |
818 | 812 |
819 protected: | 813 protected: |
820 template<class> friend class AstNodeFactory; | 814 template<class> friend class AstNodeFactory; |
821 | 815 |
822 ForStatement(Isolate* isolate, ZoneStringList* labels) | 816 ForStatement(Isolate* isolate, ZoneStringList* labels) |
823 : IterationStatement(isolate, labels), | 817 : IterationStatement(isolate, labels), |
824 init_(NULL), | 818 init_(NULL), |
825 cond_(NULL), | 819 cond_(NULL), |
826 next_(NULL), | 820 next_(NULL), |
827 may_have_function_literal_(true), | 821 may_have_function_literal_(true), |
828 loop_variable_(NULL), | 822 loop_variable_(NULL), |
829 continue_id_(GetNextId(isolate)), | 823 continue_id_(GetNextId(isolate)), |
830 body_id_(GetNextId(isolate)) { | 824 body_id_(GetNextId(isolate)) { |
831 } | 825 } |
832 | 826 |
833 private: | 827 private: |
834 Statement* init_; | 828 Statement* init_; |
835 Expression* cond_; | 829 Expression* cond_; |
836 Statement* next_; | 830 Statement* next_; |
837 // True if there is a function literal subexpression in the condition. | 831 // True if there is a function literal subexpression in the condition. |
838 bool may_have_function_literal_; | 832 bool may_have_function_literal_; |
839 Variable* loop_variable_; | 833 Variable* loop_variable_; |
840 const int continue_id_; | 834 const BailoutId continue_id_; |
841 const int body_id_; | 835 const BailoutId body_id_; |
842 }; | 836 }; |
843 | 837 |
844 | 838 |
845 class ForInStatement: public IterationStatement { | 839 class ForInStatement: public IterationStatement { |
846 public: | 840 public: |
847 DECLARE_NODE_TYPE(ForInStatement) | 841 DECLARE_NODE_TYPE(ForInStatement) |
848 | 842 |
849 void Initialize(Expression* each, Expression* enumerable, Statement* body) { | 843 void Initialize(Expression* each, Expression* enumerable, Statement* body) { |
850 IterationStatement::Initialize(body); | 844 IterationStatement::Initialize(body); |
851 each_ = each; | 845 each_ = each; |
852 enumerable_ = enumerable; | 846 enumerable_ = enumerable; |
853 } | 847 } |
854 | 848 |
855 Expression* each() const { return each_; } | 849 Expression* each() const { return each_; } |
856 Expression* enumerable() const { return enumerable_; } | 850 Expression* enumerable() const { return enumerable_; } |
857 | 851 |
858 virtual int ContinueId() const { return EntryId(); } | 852 virtual BailoutId ContinueId() const { return EntryId(); } |
859 virtual int StackCheckId() const { return body_id_; } | 853 virtual BailoutId StackCheckId() const { return body_id_; } |
860 int BodyId() const { return body_id_; } | 854 BailoutId BodyId() const { return body_id_; } |
861 int PrepareId() const { return prepare_id_; } | 855 BailoutId PrepareId() const { return prepare_id_; } |
| 856 |
| 857 TypeFeedbackId ForInFeedbackId() const { return reuse(PrepareId()); } |
862 | 858 |
863 protected: | 859 protected: |
864 template<class> friend class AstNodeFactory; | 860 template<class> friend class AstNodeFactory; |
865 | 861 |
866 ForInStatement(Isolate* isolate, ZoneStringList* labels) | 862 ForInStatement(Isolate* isolate, ZoneStringList* labels) |
867 : IterationStatement(isolate, labels), | 863 : IterationStatement(isolate, labels), |
868 each_(NULL), | 864 each_(NULL), |
869 enumerable_(NULL), | 865 enumerable_(NULL), |
870 body_id_(GetNextId(isolate)), | 866 body_id_(GetNextId(isolate)), |
871 prepare_id_(GetNextId(isolate)) { | 867 prepare_id_(GetNextId(isolate)) { |
872 } | 868 } |
873 | 869 |
874 private: | 870 private: |
875 Expression* each_; | 871 Expression* each_; |
876 Expression* enumerable_; | 872 Expression* enumerable_; |
877 const int body_id_; | 873 const BailoutId body_id_; |
878 const int prepare_id_; | 874 const BailoutId prepare_id_; |
879 }; | 875 }; |
880 | 876 |
881 | 877 |
882 class ExpressionStatement: public Statement { | 878 class ExpressionStatement: public Statement { |
883 public: | 879 public: |
884 DECLARE_NODE_TYPE(ExpressionStatement) | 880 DECLARE_NODE_TYPE(ExpressionStatement) |
885 | 881 |
886 void set_expression(Expression* e) { expression_ = e; } | 882 void set_expression(Expression* e) { expression_ = e; } |
887 Expression* expression() const { return expression_; } | 883 Expression* expression() const { return expression_; } |
888 | 884 |
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
979 Expression* label() const { | 975 Expression* label() const { |
980 CHECK(!is_default()); | 976 CHECK(!is_default()); |
981 return label_; | 977 return label_; |
982 } | 978 } |
983 Label* body_target() { return &body_target_; } | 979 Label* body_target() { return &body_target_; } |
984 ZoneList<Statement*>* statements() const { return statements_; } | 980 ZoneList<Statement*>* statements() const { return statements_; } |
985 | 981 |
986 int position() const { return position_; } | 982 int position() const { return position_; } |
987 void set_position(int pos) { position_ = pos; } | 983 void set_position(int pos) { position_ = pos; } |
988 | 984 |
989 int EntryId() { return entry_id_; } | 985 BailoutId EntryId() const { return entry_id_; } |
990 int CompareId() { return compare_id_; } | |
991 | 986 |
992 // Type feedback information. | 987 // Type feedback information. |
| 988 TypeFeedbackId CompareId() { return compare_id_; } |
993 void RecordTypeFeedback(TypeFeedbackOracle* oracle); | 989 void RecordTypeFeedback(TypeFeedbackOracle* oracle); |
994 bool IsSmiCompare() { return compare_type_ == SMI_ONLY; } | 990 bool IsSmiCompare() { return compare_type_ == SMI_ONLY; } |
995 bool IsSymbolCompare() { return compare_type_ == SYMBOL_ONLY; } | 991 bool IsSymbolCompare() { return compare_type_ == SYMBOL_ONLY; } |
996 bool IsStringCompare() { return compare_type_ == STRING_ONLY; } | 992 bool IsStringCompare() { return compare_type_ == STRING_ONLY; } |
997 bool IsObjectCompare() { return compare_type_ == OBJECT_ONLY; } | 993 bool IsObjectCompare() { return compare_type_ == OBJECT_ONLY; } |
998 | 994 |
999 private: | 995 private: |
1000 Expression* label_; | 996 Expression* label_; |
1001 Label body_target_; | 997 Label body_target_; |
1002 ZoneList<Statement*>* statements_; | 998 ZoneList<Statement*>* statements_; |
1003 int position_; | 999 int position_; |
1004 enum CompareTypeFeedback { | 1000 enum CompareTypeFeedback { |
1005 NONE, | 1001 NONE, |
1006 SMI_ONLY, | 1002 SMI_ONLY, |
1007 SYMBOL_ONLY, | 1003 SYMBOL_ONLY, |
1008 STRING_ONLY, | 1004 STRING_ONLY, |
1009 OBJECT_ONLY | 1005 OBJECT_ONLY |
1010 }; | 1006 }; |
1011 CompareTypeFeedback compare_type_; | 1007 CompareTypeFeedback compare_type_; |
1012 const int compare_id_; | 1008 const TypeFeedbackId compare_id_; |
1013 const int entry_id_; | 1009 const BailoutId entry_id_; |
1014 }; | 1010 }; |
1015 | 1011 |
1016 | 1012 |
1017 class SwitchStatement: public BreakableStatement { | 1013 class SwitchStatement: public BreakableStatement { |
1018 public: | 1014 public: |
1019 DECLARE_NODE_TYPE(SwitchStatement) | 1015 DECLARE_NODE_TYPE(SwitchStatement) |
1020 | 1016 |
1021 void Initialize(Expression* tag, ZoneList<CaseClause*>* cases) { | 1017 void Initialize(Expression* tag, ZoneList<CaseClause*>* cases) { |
1022 tag_ = tag; | 1018 tag_ = tag; |
1023 cases_ = cases; | 1019 cases_ = cases; |
(...skipping 25 matching lines...) Expand all Loading... |
1049 public: | 1045 public: |
1050 DECLARE_NODE_TYPE(IfStatement) | 1046 DECLARE_NODE_TYPE(IfStatement) |
1051 | 1047 |
1052 bool HasThenStatement() const { return !then_statement()->IsEmpty(); } | 1048 bool HasThenStatement() const { return !then_statement()->IsEmpty(); } |
1053 bool HasElseStatement() const { return !else_statement()->IsEmpty(); } | 1049 bool HasElseStatement() const { return !else_statement()->IsEmpty(); } |
1054 | 1050 |
1055 Expression* condition() const { return condition_; } | 1051 Expression* condition() const { return condition_; } |
1056 Statement* then_statement() const { return then_statement_; } | 1052 Statement* then_statement() const { return then_statement_; } |
1057 Statement* else_statement() const { return else_statement_; } | 1053 Statement* else_statement() const { return else_statement_; } |
1058 | 1054 |
1059 int IfId() const { return if_id_; } | 1055 BailoutId IfId() const { return if_id_; } |
1060 int ThenId() const { return then_id_; } | 1056 BailoutId ThenId() const { return then_id_; } |
1061 int ElseId() const { return else_id_; } | 1057 BailoutId ElseId() const { return else_id_; } |
1062 | 1058 |
1063 protected: | 1059 protected: |
1064 template<class> friend class AstNodeFactory; | 1060 template<class> friend class AstNodeFactory; |
1065 | 1061 |
1066 IfStatement(Isolate* isolate, | 1062 IfStatement(Isolate* isolate, |
1067 Expression* condition, | 1063 Expression* condition, |
1068 Statement* then_statement, | 1064 Statement* then_statement, |
1069 Statement* else_statement) | 1065 Statement* else_statement) |
1070 : condition_(condition), | 1066 : condition_(condition), |
1071 then_statement_(then_statement), | 1067 then_statement_(then_statement), |
1072 else_statement_(else_statement), | 1068 else_statement_(else_statement), |
1073 if_id_(GetNextId(isolate)), | 1069 if_id_(GetNextId(isolate)), |
1074 then_id_(GetNextId(isolate)), | 1070 then_id_(GetNextId(isolate)), |
1075 else_id_(GetNextId(isolate)) { | 1071 else_id_(GetNextId(isolate)) { |
1076 } | 1072 } |
1077 | 1073 |
1078 private: | 1074 private: |
1079 Expression* condition_; | 1075 Expression* condition_; |
1080 Statement* then_statement_; | 1076 Statement* then_statement_; |
1081 Statement* else_statement_; | 1077 Statement* else_statement_; |
1082 const int if_id_; | 1078 const BailoutId if_id_; |
1083 const int then_id_; | 1079 const BailoutId then_id_; |
1084 const int else_id_; | 1080 const BailoutId else_id_; |
1085 }; | 1081 }; |
1086 | 1082 |
1087 | 1083 |
1088 // NOTE: TargetCollectors are represented as nodes to fit in the target | 1084 // NOTE: TargetCollectors are represented as nodes to fit in the target |
1089 // stack in the compiler; this should probably be reworked. | 1085 // stack in the compiler; this should probably be reworked. |
1090 class TargetCollector: public AstNode { | 1086 class TargetCollector: public AstNode { |
1091 public: | 1087 public: |
1092 explicit TargetCollector(Zone* zone) : targets_(0, zone) { } | 1088 explicit TargetCollector(Zone* zone) : targets_(0, zone) { } |
1093 | 1089 |
1094 // Adds a jump target to the collector. The collector stores a pointer not | 1090 // Adds a jump target to the collector. The collector stores a pointer not |
(...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1241 // Support for using Literal as a HashMap key. NOTE: Currently, this works | 1237 // Support for using Literal as a HashMap key. NOTE: Currently, this works |
1242 // only for string and number literals! | 1238 // only for string and number literals! |
1243 uint32_t Hash() { return ToString()->Hash(); } | 1239 uint32_t Hash() { return ToString()->Hash(); } |
1244 | 1240 |
1245 static bool Match(void* literal1, void* literal2) { | 1241 static bool Match(void* literal1, void* literal2) { |
1246 Handle<String> s1 = static_cast<Literal*>(literal1)->ToString(); | 1242 Handle<String> s1 = static_cast<Literal*>(literal1)->ToString(); |
1247 Handle<String> s2 = static_cast<Literal*>(literal2)->ToString(); | 1243 Handle<String> s2 = static_cast<Literal*>(literal2)->ToString(); |
1248 return s1->Equals(*s2); | 1244 return s1->Equals(*s2); |
1249 } | 1245 } |
1250 | 1246 |
| 1247 TypeFeedbackId LiteralFeedbackId() const { return reuse(id()); } |
| 1248 |
1251 protected: | 1249 protected: |
1252 template<class> friend class AstNodeFactory; | 1250 template<class> friend class AstNodeFactory; |
1253 | 1251 |
1254 Literal(Isolate* isolate, Handle<Object> handle) | 1252 Literal(Isolate* isolate, Handle<Object> handle) |
1255 : Expression(isolate), | 1253 : Expression(isolate), |
1256 handle_(handle) { } | 1254 handle_(handle) { } |
1257 | 1255 |
1258 private: | 1256 private: |
1259 Handle<String> ToString(); | 1257 Handle<String> ToString(); |
1260 | 1258 |
(...skipping 158 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1419 // An array literal has a literals object that is used | 1417 // An array literal has a literals object that is used |
1420 // for minimizing the work when constructing it at runtime. | 1418 // for minimizing the work when constructing it at runtime. |
1421 class ArrayLiteral: public MaterializedLiteral { | 1419 class ArrayLiteral: public MaterializedLiteral { |
1422 public: | 1420 public: |
1423 DECLARE_NODE_TYPE(ArrayLiteral) | 1421 DECLARE_NODE_TYPE(ArrayLiteral) |
1424 | 1422 |
1425 Handle<FixedArray> constant_elements() const { return constant_elements_; } | 1423 Handle<FixedArray> constant_elements() const { return constant_elements_; } |
1426 ZoneList<Expression*>* values() const { return values_; } | 1424 ZoneList<Expression*>* values() const { return values_; } |
1427 | 1425 |
1428 // Return an AST id for an element that is used in simulate instructions. | 1426 // Return an AST id for an element that is used in simulate instructions. |
1429 int GetIdForElement(int i) { return first_element_id_ + i; } | 1427 BailoutId GetIdForElement(int i) { |
| 1428 return BailoutId(first_element_id_.ToInt() + i); |
| 1429 } |
1430 | 1430 |
1431 protected: | 1431 protected: |
1432 template<class> friend class AstNodeFactory; | 1432 template<class> friend class AstNodeFactory; |
1433 | 1433 |
1434 ArrayLiteral(Isolate* isolate, | 1434 ArrayLiteral(Isolate* isolate, |
1435 Handle<FixedArray> constant_elements, | 1435 Handle<FixedArray> constant_elements, |
1436 ZoneList<Expression*>* values, | 1436 ZoneList<Expression*>* values, |
1437 int literal_index, | 1437 int literal_index, |
1438 bool is_simple, | 1438 bool is_simple, |
1439 int depth) | 1439 int depth) |
1440 : MaterializedLiteral(isolate, literal_index, is_simple, depth), | 1440 : MaterializedLiteral(isolate, literal_index, is_simple, depth), |
1441 constant_elements_(constant_elements), | 1441 constant_elements_(constant_elements), |
1442 values_(values), | 1442 values_(values), |
1443 first_element_id_(ReserveIdRange(isolate, values->length())) {} | 1443 first_element_id_(ReserveIdRange(isolate, values->length())) {} |
1444 | 1444 |
1445 private: | 1445 private: |
1446 Handle<FixedArray> constant_elements_; | 1446 Handle<FixedArray> constant_elements_; |
1447 ZoneList<Expression*>* values_; | 1447 ZoneList<Expression*>* values_; |
1448 const int first_element_id_; | 1448 const BailoutId first_element_id_; |
1449 }; | 1449 }; |
1450 | 1450 |
1451 | 1451 |
1452 class VariableProxy: public Expression { | 1452 class VariableProxy: public Expression { |
1453 public: | 1453 public: |
1454 DECLARE_NODE_TYPE(VariableProxy) | 1454 DECLARE_NODE_TYPE(VariableProxy) |
1455 | 1455 |
1456 virtual bool IsValidLeftHandSide() { | 1456 virtual bool IsValidLeftHandSide() { |
1457 return var_ == NULL ? true : var_->IsValidLeftHandSide(); | 1457 return var_ == NULL ? true : var_->IsValidLeftHandSide(); |
1458 } | 1458 } |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1506 class Property: public Expression { | 1506 class Property: public Expression { |
1507 public: | 1507 public: |
1508 DECLARE_NODE_TYPE(Property) | 1508 DECLARE_NODE_TYPE(Property) |
1509 | 1509 |
1510 virtual bool IsValidLeftHandSide() { return true; } | 1510 virtual bool IsValidLeftHandSide() { return true; } |
1511 | 1511 |
1512 Expression* obj() const { return obj_; } | 1512 Expression* obj() const { return obj_; } |
1513 Expression* key() const { return key_; } | 1513 Expression* key() const { return key_; } |
1514 virtual int position() const { return pos_; } | 1514 virtual int position() const { return pos_; } |
1515 | 1515 |
1516 // Bailout support. | 1516 BailoutId ReturnId() const { return return_id_; } |
1517 int ReturnId() const { return return_id_; } | |
1518 | 1517 |
1519 bool IsStringLength() const { return is_string_length_; } | 1518 bool IsStringLength() const { return is_string_length_; } |
1520 bool IsStringAccess() const { return is_string_access_; } | 1519 bool IsStringAccess() const { return is_string_access_; } |
1521 bool IsFunctionPrototype() const { return is_function_prototype_; } | 1520 bool IsFunctionPrototype() const { return is_function_prototype_; } |
1522 | 1521 |
1523 // Type feedback information. | 1522 // Type feedback information. |
1524 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* zone); | 1523 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* zone); |
1525 virtual bool IsMonomorphic() { return is_monomorphic_; } | 1524 virtual bool IsMonomorphic() { return is_monomorphic_; } |
1526 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } | 1525 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } |
1527 bool IsArrayLength() { return is_array_length_; } | 1526 bool IsArrayLength() { return is_array_length_; } |
1528 bool IsUninitialized() { return is_uninitialized_; } | 1527 bool IsUninitialized() { return is_uninitialized_; } |
| 1528 TypeFeedbackId PropertyFeedbackId() { return reuse(id()); } |
1529 | 1529 |
1530 protected: | 1530 protected: |
1531 template<class> friend class AstNodeFactory; | 1531 template<class> friend class AstNodeFactory; |
1532 | 1532 |
1533 Property(Isolate* isolate, | 1533 Property(Isolate* isolate, |
1534 Expression* obj, | 1534 Expression* obj, |
1535 Expression* key, | 1535 Expression* key, |
1536 int pos) | 1536 int pos) |
1537 : Expression(isolate), | 1537 : Expression(isolate), |
1538 obj_(obj), | 1538 obj_(obj), |
1539 key_(key), | 1539 key_(key), |
1540 pos_(pos), | 1540 pos_(pos), |
1541 return_id_(GetNextId(isolate)), | 1541 return_id_(GetNextId(isolate)), |
1542 is_monomorphic_(false), | 1542 is_monomorphic_(false), |
1543 is_uninitialized_(false), | 1543 is_uninitialized_(false), |
1544 is_array_length_(false), | 1544 is_array_length_(false), |
1545 is_string_length_(false), | 1545 is_string_length_(false), |
1546 is_string_access_(false), | 1546 is_string_access_(false), |
1547 is_function_prototype_(false) { } | 1547 is_function_prototype_(false) { } |
1548 | 1548 |
1549 private: | 1549 private: |
1550 Expression* obj_; | 1550 Expression* obj_; |
1551 Expression* key_; | 1551 Expression* key_; |
1552 int pos_; | 1552 int pos_; |
1553 const int return_id_; | 1553 const BailoutId return_id_; |
1554 | 1554 |
1555 SmallMapList receiver_types_; | 1555 SmallMapList receiver_types_; |
1556 bool is_monomorphic_ : 1; | 1556 bool is_monomorphic_ : 1; |
1557 bool is_uninitialized_ : 1; | 1557 bool is_uninitialized_ : 1; |
1558 bool is_array_length_ : 1; | 1558 bool is_array_length_ : 1; |
1559 bool is_string_length_ : 1; | 1559 bool is_string_length_ : 1; |
1560 bool is_string_access_ : 1; | 1560 bool is_string_access_ : 1; |
1561 bool is_function_prototype_ : 1; | 1561 bool is_function_prototype_ : 1; |
1562 }; | 1562 }; |
1563 | 1563 |
1564 | 1564 |
1565 class Call: public Expression { | 1565 class Call: public Expression { |
1566 public: | 1566 public: |
1567 DECLARE_NODE_TYPE(Call) | 1567 DECLARE_NODE_TYPE(Call) |
1568 | 1568 |
1569 Expression* expression() const { return expression_; } | 1569 Expression* expression() const { return expression_; } |
1570 ZoneList<Expression*>* arguments() const { return arguments_; } | 1570 ZoneList<Expression*>* arguments() const { return arguments_; } |
1571 virtual int position() const { return pos_; } | 1571 virtual int position() const { return pos_; } |
1572 | 1572 |
1573 void RecordTypeFeedback(TypeFeedbackOracle* oracle, | 1573 // Type feedback information. |
1574 CallKind call_kind); | 1574 TypeFeedbackId CallFeedbackId() const { return reuse(id()); } |
| 1575 void RecordTypeFeedback(TypeFeedbackOracle* oracle, CallKind call_kind); |
1575 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } | 1576 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } |
1576 virtual bool IsMonomorphic() { return is_monomorphic_; } | 1577 virtual bool IsMonomorphic() { return is_monomorphic_; } |
1577 CheckType check_type() const { return check_type_; } | 1578 CheckType check_type() const { return check_type_; } |
1578 Handle<JSFunction> target() { return target_; } | 1579 Handle<JSFunction> target() { return target_; } |
1579 | 1580 |
1580 // A cache for the holder, set as a side effect of computing the target of the | 1581 // A cache for the holder, set as a side effect of computing the target of the |
1581 // call. Note that it contains the null handle when the receiver is the same | 1582 // call. Note that it contains the null handle when the receiver is the same |
1582 // as the holder! | 1583 // as the holder! |
1583 Handle<JSObject> holder() { return holder_; } | 1584 Handle<JSObject> holder() { return holder_; } |
1584 | 1585 |
1585 Handle<JSGlobalPropertyCell> cell() { return cell_; } | 1586 Handle<JSGlobalPropertyCell> cell() { return cell_; } |
1586 | 1587 |
1587 bool ComputeTarget(Handle<Map> type, Handle<String> name); | 1588 bool ComputeTarget(Handle<Map> type, Handle<String> name); |
1588 bool ComputeGlobalTarget(Handle<GlobalObject> global, LookupResult* lookup); | 1589 bool ComputeGlobalTarget(Handle<GlobalObject> global, LookupResult* lookup); |
1589 | 1590 |
1590 // Bailout support. | 1591 BailoutId ReturnId() const { return return_id_; } |
1591 int ReturnId() const { return return_id_; } | |
1592 | 1592 |
1593 #ifdef DEBUG | 1593 #ifdef DEBUG |
1594 // Used to assert that the FullCodeGenerator records the return site. | 1594 // Used to assert that the FullCodeGenerator records the return site. |
1595 bool return_is_recorded_; | 1595 bool return_is_recorded_; |
1596 #endif | 1596 #endif |
1597 | 1597 |
1598 protected: | 1598 protected: |
1599 template<class> friend class AstNodeFactory; | 1599 template<class> friend class AstNodeFactory; |
1600 | 1600 |
1601 Call(Isolate* isolate, | 1601 Call(Isolate* isolate, |
(...skipping 13 matching lines...) Expand all Loading... |
1615 ZoneList<Expression*>* arguments_; | 1615 ZoneList<Expression*>* arguments_; |
1616 int pos_; | 1616 int pos_; |
1617 | 1617 |
1618 bool is_monomorphic_; | 1618 bool is_monomorphic_; |
1619 CheckType check_type_; | 1619 CheckType check_type_; |
1620 SmallMapList receiver_types_; | 1620 SmallMapList receiver_types_; |
1621 Handle<JSFunction> target_; | 1621 Handle<JSFunction> target_; |
1622 Handle<JSObject> holder_; | 1622 Handle<JSObject> holder_; |
1623 Handle<JSGlobalPropertyCell> cell_; | 1623 Handle<JSGlobalPropertyCell> cell_; |
1624 | 1624 |
1625 const int return_id_; | 1625 const BailoutId return_id_; |
1626 }; | 1626 }; |
1627 | 1627 |
1628 | 1628 |
1629 class CallNew: public Expression { | 1629 class CallNew: public Expression { |
1630 public: | 1630 public: |
1631 DECLARE_NODE_TYPE(CallNew) | 1631 DECLARE_NODE_TYPE(CallNew) |
1632 | 1632 |
1633 Expression* expression() const { return expression_; } | 1633 Expression* expression() const { return expression_; } |
1634 ZoneList<Expression*>* arguments() const { return arguments_; } | 1634 ZoneList<Expression*>* arguments() const { return arguments_; } |
1635 virtual int position() const { return pos_; } | 1635 virtual int position() const { return pos_; } |
1636 | 1636 |
| 1637 // Type feedback information. |
| 1638 TypeFeedbackId CallNewFeedbackId() const { return reuse(id()); } |
1637 void RecordTypeFeedback(TypeFeedbackOracle* oracle); | 1639 void RecordTypeFeedback(TypeFeedbackOracle* oracle); |
1638 virtual bool IsMonomorphic() { return is_monomorphic_; } | 1640 virtual bool IsMonomorphic() { return is_monomorphic_; } |
1639 Handle<JSFunction> target() { return target_; } | 1641 Handle<JSFunction> target() { return target_; } |
1640 | 1642 |
1641 // Bailout support. | 1643 BailoutId ReturnId() const { return return_id_; } |
1642 int ReturnId() const { return return_id_; } | |
1643 | 1644 |
1644 protected: | 1645 protected: |
1645 template<class> friend class AstNodeFactory; | 1646 template<class> friend class AstNodeFactory; |
1646 | 1647 |
1647 CallNew(Isolate* isolate, | 1648 CallNew(Isolate* isolate, |
1648 Expression* expression, | 1649 Expression* expression, |
1649 ZoneList<Expression*>* arguments, | 1650 ZoneList<Expression*>* arguments, |
1650 int pos) | 1651 int pos) |
1651 : Expression(isolate), | 1652 : Expression(isolate), |
1652 expression_(expression), | 1653 expression_(expression), |
1653 arguments_(arguments), | 1654 arguments_(arguments), |
1654 pos_(pos), | 1655 pos_(pos), |
1655 is_monomorphic_(false), | 1656 is_monomorphic_(false), |
1656 return_id_(GetNextId(isolate)) { } | 1657 return_id_(GetNextId(isolate)) { } |
1657 | 1658 |
1658 private: | 1659 private: |
1659 Expression* expression_; | 1660 Expression* expression_; |
1660 ZoneList<Expression*>* arguments_; | 1661 ZoneList<Expression*>* arguments_; |
1661 int pos_; | 1662 int pos_; |
1662 | 1663 |
1663 bool is_monomorphic_; | 1664 bool is_monomorphic_; |
1664 Handle<JSFunction> target_; | 1665 Handle<JSFunction> target_; |
1665 | 1666 |
1666 const int return_id_; | 1667 const BailoutId return_id_; |
1667 }; | 1668 }; |
1668 | 1669 |
1669 | 1670 |
1670 // The CallRuntime class does not represent any official JavaScript | 1671 // The CallRuntime class does not represent any official JavaScript |
1671 // language construct. Instead it is used to call a C or JS function | 1672 // language construct. Instead it is used to call a C or JS function |
1672 // with a set of arguments. This is used from the builtins that are | 1673 // with a set of arguments. This is used from the builtins that are |
1673 // implemented in JavaScript (see "v8natives.js"). | 1674 // implemented in JavaScript (see "v8natives.js"). |
1674 class CallRuntime: public Expression { | 1675 class CallRuntime: public Expression { |
1675 public: | 1676 public: |
1676 DECLARE_NODE_TYPE(CallRuntime) | 1677 DECLARE_NODE_TYPE(CallRuntime) |
1677 | 1678 |
1678 Handle<String> name() const { return name_; } | 1679 Handle<String> name() const { return name_; } |
1679 const Runtime::Function* function() const { return function_; } | 1680 const Runtime::Function* function() const { return function_; } |
1680 ZoneList<Expression*>* arguments() const { return arguments_; } | 1681 ZoneList<Expression*>* arguments() const { return arguments_; } |
1681 bool is_jsruntime() const { return function_ == NULL; } | 1682 bool is_jsruntime() const { return function_ == NULL; } |
1682 | 1683 |
| 1684 TypeFeedbackId CallRuntimeFeedbackId() const { return reuse(id()); } |
| 1685 |
1683 protected: | 1686 protected: |
1684 template<class> friend class AstNodeFactory; | 1687 template<class> friend class AstNodeFactory; |
1685 | 1688 |
1686 CallRuntime(Isolate* isolate, | 1689 CallRuntime(Isolate* isolate, |
1687 Handle<String> name, | 1690 Handle<String> name, |
1688 const Runtime::Function* function, | 1691 const Runtime::Function* function, |
1689 ZoneList<Expression*>* arguments) | 1692 ZoneList<Expression*>* arguments) |
1690 : Expression(isolate), | 1693 : Expression(isolate), |
1691 name_(name), | 1694 name_(name), |
1692 function_(function), | 1695 function_(function), |
1693 arguments_(arguments) { } | 1696 arguments_(arguments) { } |
1694 | 1697 |
1695 private: | 1698 private: |
1696 Handle<String> name_; | 1699 Handle<String> name_; |
1697 const Runtime::Function* function_; | 1700 const Runtime::Function* function_; |
1698 ZoneList<Expression*>* arguments_; | 1701 ZoneList<Expression*>* arguments_; |
1699 }; | 1702 }; |
1700 | 1703 |
1701 | 1704 |
1702 class UnaryOperation: public Expression { | 1705 class UnaryOperation: public Expression { |
1703 public: | 1706 public: |
1704 DECLARE_NODE_TYPE(UnaryOperation) | 1707 DECLARE_NODE_TYPE(UnaryOperation) |
1705 | 1708 |
1706 virtual bool ResultOverwriteAllowed(); | 1709 virtual bool ResultOverwriteAllowed(); |
1707 | 1710 |
1708 Token::Value op() const { return op_; } | 1711 Token::Value op() const { return op_; } |
1709 Expression* expression() const { return expression_; } | 1712 Expression* expression() const { return expression_; } |
1710 virtual int position() const { return pos_; } | 1713 virtual int position() const { return pos_; } |
1711 | 1714 |
1712 int MaterializeTrueId() { return materialize_true_id_; } | 1715 BailoutId MaterializeTrueId() { return materialize_true_id_; } |
1713 int MaterializeFalseId() { return materialize_false_id_; } | 1716 BailoutId MaterializeFalseId() { return materialize_false_id_; } |
| 1717 |
| 1718 TypeFeedbackId UnaryOperationFeedbackId() const { return reuse(id()); } |
1714 | 1719 |
1715 protected: | 1720 protected: |
1716 template<class> friend class AstNodeFactory; | 1721 template<class> friend class AstNodeFactory; |
1717 | 1722 |
1718 UnaryOperation(Isolate* isolate, | 1723 UnaryOperation(Isolate* isolate, |
1719 Token::Value op, | 1724 Token::Value op, |
1720 Expression* expression, | 1725 Expression* expression, |
1721 int pos) | 1726 int pos) |
1722 : Expression(isolate), | 1727 : Expression(isolate), |
1723 op_(op), | 1728 op_(op), |
1724 expression_(expression), | 1729 expression_(expression), |
1725 pos_(pos), | 1730 pos_(pos), |
1726 materialize_true_id_(GetNextId(isolate)), | 1731 materialize_true_id_(GetNextId(isolate)), |
1727 materialize_false_id_(GetNextId(isolate)) { | 1732 materialize_false_id_(GetNextId(isolate)) { |
1728 ASSERT(Token::IsUnaryOp(op)); | 1733 ASSERT(Token::IsUnaryOp(op)); |
1729 } | 1734 } |
1730 | 1735 |
1731 private: | 1736 private: |
1732 Token::Value op_; | 1737 Token::Value op_; |
1733 Expression* expression_; | 1738 Expression* expression_; |
1734 int pos_; | 1739 int pos_; |
1735 | 1740 |
1736 // For unary not (Token::NOT), the AST ids where true and false will | 1741 // For unary not (Token::NOT), the AST ids where true and false will |
1737 // actually be materialized, respectively. | 1742 // actually be materialized, respectively. |
1738 const int materialize_true_id_; | 1743 const BailoutId materialize_true_id_; |
1739 const int materialize_false_id_; | 1744 const BailoutId materialize_false_id_; |
1740 }; | 1745 }; |
1741 | 1746 |
1742 | 1747 |
1743 class BinaryOperation: public Expression { | 1748 class BinaryOperation: public Expression { |
1744 public: | 1749 public: |
1745 DECLARE_NODE_TYPE(BinaryOperation) | 1750 DECLARE_NODE_TYPE(BinaryOperation) |
1746 | 1751 |
1747 virtual bool ResultOverwriteAllowed(); | 1752 virtual bool ResultOverwriteAllowed(); |
1748 | 1753 |
1749 Token::Value op() const { return op_; } | 1754 Token::Value op() const { return op_; } |
1750 Expression* left() const { return left_; } | 1755 Expression* left() const { return left_; } |
1751 Expression* right() const { return right_; } | 1756 Expression* right() const { return right_; } |
1752 virtual int position() const { return pos_; } | 1757 virtual int position() const { return pos_; } |
1753 | 1758 |
1754 // Bailout support. | 1759 BailoutId RightId() const { return right_id_; } |
1755 int RightId() const { return right_id_; } | 1760 |
| 1761 TypeFeedbackId BinaryOperationFeedbackId() const { return reuse(id()); } |
1756 | 1762 |
1757 protected: | 1763 protected: |
1758 template<class> friend class AstNodeFactory; | 1764 template<class> friend class AstNodeFactory; |
1759 | 1765 |
1760 BinaryOperation(Isolate* isolate, | 1766 BinaryOperation(Isolate* isolate, |
1761 Token::Value op, | 1767 Token::Value op, |
1762 Expression* left, | 1768 Expression* left, |
1763 Expression* right, | 1769 Expression* right, |
1764 int pos) | 1770 int pos) |
1765 : Expression(isolate), | 1771 : Expression(isolate), |
1766 op_(op), | 1772 op_(op), |
1767 left_(left), | 1773 left_(left), |
1768 right_(right), | 1774 right_(right), |
1769 pos_(pos), | 1775 pos_(pos), |
1770 right_id_(GetNextId(isolate)) { | 1776 right_id_(GetNextId(isolate)) { |
1771 ASSERT(Token::IsBinaryOp(op)); | 1777 ASSERT(Token::IsBinaryOp(op)); |
1772 } | 1778 } |
1773 | 1779 |
1774 private: | 1780 private: |
1775 Token::Value op_; | 1781 Token::Value op_; |
1776 Expression* left_; | 1782 Expression* left_; |
1777 Expression* right_; | 1783 Expression* right_; |
1778 int pos_; | 1784 int pos_; |
1779 // The short-circuit logical operations need an AST ID for their | 1785 // The short-circuit logical operations need an AST ID for their |
1780 // right-hand subexpression. | 1786 // right-hand subexpression. |
1781 const int right_id_; | 1787 const BailoutId right_id_; |
1782 }; | 1788 }; |
1783 | 1789 |
1784 | 1790 |
1785 class CountOperation: public Expression { | 1791 class CountOperation: public Expression { |
1786 public: | 1792 public: |
1787 DECLARE_NODE_TYPE(CountOperation) | 1793 DECLARE_NODE_TYPE(CountOperation) |
1788 | 1794 |
1789 bool is_prefix() const { return is_prefix_; } | 1795 bool is_prefix() const { return is_prefix_; } |
1790 bool is_postfix() const { return !is_prefix_; } | 1796 bool is_postfix() const { return !is_prefix_; } |
1791 | 1797 |
1792 Token::Value op() const { return op_; } | 1798 Token::Value op() const { return op_; } |
1793 Token::Value binary_op() { | 1799 Token::Value binary_op() { |
1794 return (op() == Token::INC) ? Token::ADD : Token::SUB; | 1800 return (op() == Token::INC) ? Token::ADD : Token::SUB; |
1795 } | 1801 } |
1796 | 1802 |
1797 Expression* expression() const { return expression_; } | 1803 Expression* expression() const { return expression_; } |
1798 virtual int position() const { return pos_; } | 1804 virtual int position() const { return pos_; } |
1799 | 1805 |
1800 virtual void MarkAsStatement() { is_prefix_ = true; } | 1806 virtual void MarkAsStatement() { is_prefix_ = true; } |
1801 | 1807 |
1802 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* znoe); | 1808 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* znoe); |
1803 virtual bool IsMonomorphic() { return is_monomorphic_; } | 1809 virtual bool IsMonomorphic() { return is_monomorphic_; } |
1804 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } | 1810 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } |
1805 | 1811 |
1806 // Bailout support. | 1812 BailoutId AssignmentId() const { return assignment_id_; } |
1807 int AssignmentId() const { return assignment_id_; } | 1813 BailoutId CountId() const { return count_id_; } |
1808 int CountId() const { return count_id_; } | 1814 |
| 1815 TypeFeedbackId CountBinOpFeedbackId() const { return reuse(CountId()); } |
| 1816 TypeFeedbackId CountStoreFeedbackId() const { return reuse(id()); } |
| 1817 |
1809 | 1818 |
1810 protected: | 1819 protected: |
1811 template<class> friend class AstNodeFactory; | 1820 template<class> friend class AstNodeFactory; |
1812 | 1821 |
1813 CountOperation(Isolate* isolate, | 1822 CountOperation(Isolate* isolate, |
1814 Token::Value op, | 1823 Token::Value op, |
1815 bool is_prefix, | 1824 bool is_prefix, |
1816 Expression* expr, | 1825 Expression* expr, |
1817 int pos) | 1826 int pos) |
1818 : Expression(isolate), | 1827 : Expression(isolate), |
1819 op_(op), | 1828 op_(op), |
1820 is_prefix_(is_prefix), | 1829 is_prefix_(is_prefix), |
1821 expression_(expr), | 1830 expression_(expr), |
1822 pos_(pos), | 1831 pos_(pos), |
1823 assignment_id_(GetNextId(isolate)), | 1832 assignment_id_(GetNextId(isolate)), |
1824 count_id_(GetNextId(isolate)) {} | 1833 count_id_(GetNextId(isolate)) {} |
1825 | 1834 |
1826 private: | 1835 private: |
1827 Token::Value op_; | 1836 Token::Value op_; |
1828 bool is_prefix_; | 1837 bool is_prefix_; |
1829 bool is_monomorphic_; | 1838 bool is_monomorphic_; |
1830 Expression* expression_; | 1839 Expression* expression_; |
1831 int pos_; | 1840 int pos_; |
1832 const int assignment_id_; | 1841 const BailoutId assignment_id_; |
1833 const int count_id_; | 1842 const BailoutId count_id_; |
1834 SmallMapList receiver_types_; | 1843 SmallMapList receiver_types_; |
1835 }; | 1844 }; |
1836 | 1845 |
1837 | 1846 |
1838 class CompareOperation: public Expression { | 1847 class CompareOperation: public Expression { |
1839 public: | 1848 public: |
1840 DECLARE_NODE_TYPE(CompareOperation) | 1849 DECLARE_NODE_TYPE(CompareOperation) |
1841 | 1850 |
1842 Token::Value op() const { return op_; } | 1851 Token::Value op() const { return op_; } |
1843 Expression* left() const { return left_; } | 1852 Expression* left() const { return left_; } |
1844 Expression* right() const { return right_; } | 1853 Expression* right() const { return right_; } |
1845 virtual int position() const { return pos_; } | 1854 virtual int position() const { return pos_; } |
1846 | 1855 |
1847 // Type feedback information. | 1856 // Type feedback information. |
| 1857 TypeFeedbackId CompareOperationFeedbackId() const { return reuse(id()); } |
1848 void RecordTypeFeedback(TypeFeedbackOracle* oracle); | 1858 void RecordTypeFeedback(TypeFeedbackOracle* oracle); |
1849 bool IsSmiCompare() { return compare_type_ == SMI_ONLY; } | 1859 bool IsSmiCompare() { return compare_type_ == SMI_ONLY; } |
1850 bool IsObjectCompare() { return compare_type_ == OBJECT_ONLY; } | 1860 bool IsObjectCompare() { return compare_type_ == OBJECT_ONLY; } |
1851 | 1861 |
1852 // Match special cases. | 1862 // Match special cases. |
1853 bool IsLiteralCompareTypeof(Expression** expr, Handle<String>* check); | 1863 bool IsLiteralCompareTypeof(Expression** expr, Handle<String>* check); |
1854 bool IsLiteralCompareUndefined(Expression** expr); | 1864 bool IsLiteralCompareUndefined(Expression** expr); |
1855 bool IsLiteralCompareNull(Expression** expr); | 1865 bool IsLiteralCompareNull(Expression** expr); |
1856 | 1866 |
1857 protected: | 1867 protected: |
(...skipping 28 matching lines...) Expand all Loading... |
1886 public: | 1896 public: |
1887 DECLARE_NODE_TYPE(Conditional) | 1897 DECLARE_NODE_TYPE(Conditional) |
1888 | 1898 |
1889 Expression* condition() const { return condition_; } | 1899 Expression* condition() const { return condition_; } |
1890 Expression* then_expression() const { return then_expression_; } | 1900 Expression* then_expression() const { return then_expression_; } |
1891 Expression* else_expression() const { return else_expression_; } | 1901 Expression* else_expression() const { return else_expression_; } |
1892 | 1902 |
1893 int then_expression_position() const { return then_expression_position_; } | 1903 int then_expression_position() const { return then_expression_position_; } |
1894 int else_expression_position() const { return else_expression_position_; } | 1904 int else_expression_position() const { return else_expression_position_; } |
1895 | 1905 |
1896 int ThenId() const { return then_id_; } | 1906 BailoutId ThenId() const { return then_id_; } |
1897 int ElseId() const { return else_id_; } | 1907 BailoutId ElseId() const { return else_id_; } |
1898 | 1908 |
1899 protected: | 1909 protected: |
1900 template<class> friend class AstNodeFactory; | 1910 template<class> friend class AstNodeFactory; |
1901 | 1911 |
1902 Conditional(Isolate* isolate, | 1912 Conditional(Isolate* isolate, |
1903 Expression* condition, | 1913 Expression* condition, |
1904 Expression* then_expression, | 1914 Expression* then_expression, |
1905 Expression* else_expression, | 1915 Expression* else_expression, |
1906 int then_expression_position, | 1916 int then_expression_position, |
1907 int else_expression_position) | 1917 int else_expression_position) |
1908 : Expression(isolate), | 1918 : Expression(isolate), |
1909 condition_(condition), | 1919 condition_(condition), |
1910 then_expression_(then_expression), | 1920 then_expression_(then_expression), |
1911 else_expression_(else_expression), | 1921 else_expression_(else_expression), |
1912 then_expression_position_(then_expression_position), | 1922 then_expression_position_(then_expression_position), |
1913 else_expression_position_(else_expression_position), | 1923 else_expression_position_(else_expression_position), |
1914 then_id_(GetNextId(isolate)), | 1924 then_id_(GetNextId(isolate)), |
1915 else_id_(GetNextId(isolate)) { } | 1925 else_id_(GetNextId(isolate)) { } |
1916 | 1926 |
1917 private: | 1927 private: |
1918 Expression* condition_; | 1928 Expression* condition_; |
1919 Expression* then_expression_; | 1929 Expression* then_expression_; |
1920 Expression* else_expression_; | 1930 Expression* else_expression_; |
1921 int then_expression_position_; | 1931 int then_expression_position_; |
1922 int else_expression_position_; | 1932 int else_expression_position_; |
1923 const int then_id_; | 1933 const BailoutId then_id_; |
1924 const int else_id_; | 1934 const BailoutId else_id_; |
1925 }; | 1935 }; |
1926 | 1936 |
1927 | 1937 |
1928 class Assignment: public Expression { | 1938 class Assignment: public Expression { |
1929 public: | 1939 public: |
1930 DECLARE_NODE_TYPE(Assignment) | 1940 DECLARE_NODE_TYPE(Assignment) |
1931 | 1941 |
1932 Assignment* AsSimpleAssignment() { return !is_compound() ? this : NULL; } | 1942 Assignment* AsSimpleAssignment() { return !is_compound() ? this : NULL; } |
1933 | 1943 |
1934 Token::Value binary_op() const; | 1944 Token::Value binary_op() const; |
1935 | 1945 |
1936 Token::Value op() const { return op_; } | 1946 Token::Value op() const { return op_; } |
1937 Expression* target() const { return target_; } | 1947 Expression* target() const { return target_; } |
1938 Expression* value() const { return value_; } | 1948 Expression* value() const { return value_; } |
1939 virtual int position() const { return pos_; } | 1949 virtual int position() const { return pos_; } |
1940 BinaryOperation* binary_operation() const { return binary_operation_; } | 1950 BinaryOperation* binary_operation() const { return binary_operation_; } |
1941 | 1951 |
1942 // This check relies on the definition order of token in token.h. | 1952 // This check relies on the definition order of token in token.h. |
1943 bool is_compound() const { return op() > Token::ASSIGN; } | 1953 bool is_compound() const { return op() > Token::ASSIGN; } |
1944 | 1954 |
1945 // An initialization block is a series of statments of the form | 1955 // An initialization block is a series of statments of the form |
1946 // x.y.z.a = ...; x.y.z.b = ...; etc. The parser marks the beginning and | 1956 // x.y.z.a = ...; x.y.z.b = ...; etc. The parser marks the beginning and |
1947 // ending of these blocks to allow for optimizations of initialization | 1957 // ending of these blocks to allow for optimizations of initialization |
1948 // blocks. | 1958 // blocks. |
1949 bool starts_initialization_block() { return block_start_; } | 1959 bool starts_initialization_block() { return block_start_; } |
1950 bool ends_initialization_block() { return block_end_; } | 1960 bool ends_initialization_block() { return block_end_; } |
1951 void mark_block_start() { block_start_ = true; } | 1961 void mark_block_start() { block_start_ = true; } |
1952 void mark_block_end() { block_end_ = true; } | 1962 void mark_block_end() { block_end_ = true; } |
1953 | 1963 |
| 1964 BailoutId CompoundLoadId() const { return compound_load_id_; } |
| 1965 BailoutId AssignmentId() const { return assignment_id_; } |
| 1966 |
1954 // Type feedback information. | 1967 // Type feedback information. |
| 1968 TypeFeedbackId AssignmentFeedbackId() { return reuse(id()); } |
1955 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* zone); | 1969 void RecordTypeFeedback(TypeFeedbackOracle* oracle, Zone* zone); |
1956 virtual bool IsMonomorphic() { return is_monomorphic_; } | 1970 virtual bool IsMonomorphic() { return is_monomorphic_; } |
1957 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } | 1971 virtual SmallMapList* GetReceiverTypes() { return &receiver_types_; } |
1958 | 1972 |
1959 // Bailout support. | |
1960 int CompoundLoadId() const { return compound_load_id_; } | |
1961 int AssignmentId() const { return assignment_id_; } | |
1962 | |
1963 protected: | 1973 protected: |
1964 template<class> friend class AstNodeFactory; | 1974 template<class> friend class AstNodeFactory; |
1965 | 1975 |
1966 Assignment(Isolate* isolate, | 1976 Assignment(Isolate* isolate, |
1967 Token::Value op, | 1977 Token::Value op, |
1968 Expression* target, | 1978 Expression* target, |
1969 Expression* value, | 1979 Expression* value, |
1970 int pos); | 1980 int pos); |
1971 | 1981 |
1972 template<class Visitor> | 1982 template<class Visitor> |
1973 void Init(Isolate* isolate, AstNodeFactory<Visitor>* factory) { | 1983 void Init(Isolate* isolate, AstNodeFactory<Visitor>* factory) { |
1974 ASSERT(Token::IsAssignmentOp(op_)); | 1984 ASSERT(Token::IsAssignmentOp(op_)); |
1975 if (is_compound()) { | 1985 if (is_compound()) { |
1976 binary_operation_ = | 1986 binary_operation_ = |
1977 factory->NewBinaryOperation(binary_op(), target_, value_, pos_ + 1); | 1987 factory->NewBinaryOperation(binary_op(), target_, value_, pos_ + 1); |
1978 } | 1988 } |
1979 } | 1989 } |
1980 | 1990 |
1981 private: | 1991 private: |
1982 Token::Value op_; | 1992 Token::Value op_; |
1983 Expression* target_; | 1993 Expression* target_; |
1984 Expression* value_; | 1994 Expression* value_; |
1985 int pos_; | 1995 int pos_; |
1986 BinaryOperation* binary_operation_; | 1996 BinaryOperation* binary_operation_; |
1987 const int compound_load_id_; | 1997 const BailoutId compound_load_id_; |
1988 const int assignment_id_; | 1998 const BailoutId assignment_id_; |
1989 | 1999 |
1990 bool block_start_; | 2000 bool block_start_; |
1991 bool block_end_; | 2001 bool block_end_; |
1992 | 2002 |
1993 bool is_monomorphic_; | 2003 bool is_monomorphic_; |
1994 SmallMapList receiver_types_; | 2004 SmallMapList receiver_types_; |
1995 }; | 2005 }; |
1996 | 2006 |
1997 | 2007 |
1998 class Throw: public Expression { | 2008 class Throw: public Expression { |
(...skipping 978 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2977 private: | 2987 private: |
2978 Isolate* isolate_; | 2988 Isolate* isolate_; |
2979 Zone* zone_; | 2989 Zone* zone_; |
2980 Visitor visitor_; | 2990 Visitor visitor_; |
2981 }; | 2991 }; |
2982 | 2992 |
2983 | 2993 |
2984 } } // namespace v8::internal | 2994 } } // namespace v8::internal |
2985 | 2995 |
2986 #endif // V8_AST_H_ | 2996 #endif // V8_AST_H_ |
OLD | NEW |