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

Side by Side Diff: src/parser.cc

Issue 908173003: Parsing: Make Parser not know about Isolate during background parsing. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 years, 10 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
« no previous file with comments | « src/parser.h ('k') | src/preparser.h » ('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 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/v8.h" 5 #include "src/v8.h"
6 6
7 #include "src/api.h" 7 #include "src/api.h"
8 #include "src/ast.h" 8 #include "src/ast.h"
9 #include "src/bailout-reason.h" 9 #include "src/bailout-reason.h"
10 #include "src/base/platform/platform.h" 10 #include "src/base/platform/platform.h"
(...skipping 233 matching lines...) Expand 10 before | Expand all | Expand 10 after
244 unsigned ParseData::Version() { 244 unsigned ParseData::Version() {
245 return Data()[PreparseDataConstants::kVersionOffset]; 245 return Data()[PreparseDataConstants::kVersionOffset];
246 } 246 }
247 247
248 248
249 int ParseData::FunctionsSize() { 249 int ParseData::FunctionsSize() {
250 return static_cast<int>(Data()[PreparseDataConstants::kFunctionsSizeOffset]); 250 return static_cast<int>(Data()[PreparseDataConstants::kFunctionsSizeOffset]);
251 } 251 }
252 252
253 253
254 void Parser::SetCachedData() { 254 void Parser::SetCachedData(CompilationInfo* info) {
255 if (compile_options() == ScriptCompiler::kNoCompileOptions) { 255 if (compile_options_ == ScriptCompiler::kNoCompileOptions) {
256 cached_parse_data_ = NULL; 256 cached_parse_data_ = NULL;
257 } else { 257 } else {
258 DCHECK(info_->cached_data() != NULL); 258 DCHECK(info->cached_data() != NULL);
259 if (compile_options() == ScriptCompiler::kConsumeParserCache) { 259 if (compile_options_ == ScriptCompiler::kConsumeParserCache) {
260 cached_parse_data_ = ParseData::FromCachedData(*info_->cached_data()); 260 cached_parse_data_ = ParseData::FromCachedData(*info->cached_data());
261 } 261 }
262 } 262 }
263 } 263 }
264 264
265 265
266 FunctionLiteral* Parser::DefaultConstructor(bool call_super, Scope* scope, 266 FunctionLiteral* Parser::DefaultConstructor(bool call_super, Scope* scope,
267 int pos, int end_pos) { 267 int pos, int end_pos) {
268 int materialized_literal_count = -1; 268 int materialized_literal_count = -1;
269 int expected_property_count = -1; 269 int expected_property_count = -1;
270 int handler_count = 0; 270 int handler_count = 0;
(...skipping 500 matching lines...) Expand 10 before | Expand all | Expand 10 after
771 771
772 ClassLiteral* ParserTraits::ParseClassLiteral( 772 ClassLiteral* ParserTraits::ParseClassLiteral(
773 const AstRawString* name, Scanner::Location class_name_location, 773 const AstRawString* name, Scanner::Location class_name_location,
774 bool name_is_strict_reserved, int pos, bool* ok) { 774 bool name_is_strict_reserved, int pos, bool* ok) {
775 return parser_->ParseClassLiteral(name, class_name_location, 775 return parser_->ParseClassLiteral(name, class_name_location,
776 name_is_strict_reserved, pos, ok); 776 name_is_strict_reserved, pos, ok);
777 } 777 }
778 778
779 779
780 Parser::Parser(CompilationInfo* info, ParseInfo* parse_info) 780 Parser::Parser(CompilationInfo* info, ParseInfo* parse_info)
781 : ParserBase<ParserTraits>(info->isolate(), info->zone(), &scanner_, 781 : ParserBase<ParserTraits>(info->zone(), &scanner_, parse_info->stack_limit,
782 parse_info->stack_limit, info->extension(), 782 info->extension(), info->ast_value_factory(),
783 info->ast_value_factory(), NULL, this), 783 NULL, this),
784 scanner_(parse_info->unicode_cache), 784 scanner_(parse_info->unicode_cache),
785 reusable_preparser_(NULL), 785 reusable_preparser_(NULL),
786 original_scope_(NULL), 786 original_scope_(NULL),
787 target_stack_(NULL), 787 target_stack_(NULL),
788 compile_options_(info->compile_options()),
788 cached_parse_data_(NULL), 789 cached_parse_data_(NULL),
789 info_(info),
790 parsing_lazy_arrow_parameters_(false), 790 parsing_lazy_arrow_parameters_(false),
791 has_pending_error_(false), 791 has_pending_error_(false),
792 pending_error_message_(NULL), 792 pending_error_message_(NULL),
793 pending_error_arg_(NULL), 793 pending_error_arg_(NULL),
794 pending_error_char_arg_(NULL), 794 pending_error_char_arg_(NULL),
795 total_preparse_skipped_(0), 795 total_preparse_skipped_(0),
796 pre_parse_timer_(NULL) { 796 pre_parse_timer_(NULL) {
797 DCHECK(!script().is_null() || info->source_stream() != NULL); 797 // Even though we were passed CompilationInfo, we should not store it in
798 // Parser - this makes sure that Isolate is not accidentally accessed via
799 // CompilationInfo during background parsing.
800 DCHECK(!info->script().is_null() || info->source_stream() != NULL);
798 set_allow_lazy(false); // Must be explicitly enabled. 801 set_allow_lazy(false); // Must be explicitly enabled.
799 set_allow_natives(FLAG_allow_natives_syntax || info->is_native()); 802 set_allow_natives(FLAG_allow_natives_syntax || info->is_native());
800 set_allow_harmony_scoping(!info->is_native() && FLAG_harmony_scoping); 803 set_allow_harmony_scoping(!info->is_native() && FLAG_harmony_scoping);
801 set_allow_harmony_modules(!info->is_native() && FLAG_harmony_modules); 804 set_allow_harmony_modules(!info->is_native() && FLAG_harmony_modules);
802 set_allow_harmony_arrow_functions(FLAG_harmony_arrow_functions); 805 set_allow_harmony_arrow_functions(FLAG_harmony_arrow_functions);
803 set_allow_harmony_numeric_literals(FLAG_harmony_numeric_literals); 806 set_allow_harmony_numeric_literals(FLAG_harmony_numeric_literals);
804 set_allow_harmony_classes(FLAG_harmony_classes); 807 set_allow_harmony_classes(FLAG_harmony_classes);
805 set_allow_harmony_object_literals(FLAG_harmony_object_literals); 808 set_allow_harmony_object_literals(FLAG_harmony_object_literals);
806 set_allow_harmony_templates(FLAG_harmony_templates); 809 set_allow_harmony_templates(FLAG_harmony_templates);
807 set_allow_harmony_sloppy(FLAG_harmony_sloppy); 810 set_allow_harmony_sloppy(FLAG_harmony_sloppy);
808 set_allow_harmony_unicode(FLAG_harmony_unicode); 811 set_allow_harmony_unicode(FLAG_harmony_unicode);
809 set_allow_harmony_computed_property_names( 812 set_allow_harmony_computed_property_names(
810 FLAG_harmony_computed_property_names); 813 FLAG_harmony_computed_property_names);
811 set_allow_harmony_rest_params(FLAG_harmony_rest_parameters); 814 set_allow_harmony_rest_params(FLAG_harmony_rest_parameters);
812 set_allow_strong_mode(FLAG_strong_mode); 815 set_allow_strong_mode(FLAG_strong_mode);
813 for (int feature = 0; feature < v8::Isolate::kUseCounterFeatureCount; 816 for (int feature = 0; feature < v8::Isolate::kUseCounterFeatureCount;
814 ++feature) { 817 ++feature) {
815 use_counts_[feature] = 0; 818 use_counts_[feature] = 0;
816 } 819 }
817 if (info->ast_value_factory() == NULL) { 820 if (info->ast_value_factory() == NULL) {
818 // info takes ownership of AstValueFactory. 821 // info takes ownership of AstValueFactory.
819 info->SetAstValueFactory( 822 info->SetAstValueFactory(
820 new AstValueFactory(zone(), parse_info->hash_seed)); 823 new AstValueFactory(zone(), parse_info->hash_seed));
821 ast_value_factory_ = info->ast_value_factory(); 824 ast_value_factory_ = info->ast_value_factory();
822 } 825 }
823 } 826 }
824 827
825 828
826 FunctionLiteral* Parser::ParseProgram() { 829 FunctionLiteral* Parser::ParseProgram(CompilationInfo* info) {
827 // TODO(bmeurer): We temporarily need to pass allow_nesting = true here, 830 // TODO(bmeurer): We temporarily need to pass allow_nesting = true here,
828 // see comment for HistogramTimerScope class. 831 // see comment for HistogramTimerScope class.
829 832
830 // It's OK to use the counters here, since this function is only called in 833 // It's OK to use the Isolate & counters here, since this function is only
831 // the main thread. 834 // called in the main thread.
832 HistogramTimerScope timer_scope(isolate()->counters()->parse(), true); 835 Isolate* isolate = info->isolate();
833 Handle<String> source(String::cast(script()->source())); 836 HistogramTimerScope timer_scope(isolate->counters()->parse(), true);
834 isolate()->counters()->total_parse_size()->Increment(source->length()); 837 Handle<String> source(String::cast(info->script()->source()));
838 isolate->counters()->total_parse_size()->Increment(source->length());
835 base::ElapsedTimer timer; 839 base::ElapsedTimer timer;
836 if (FLAG_trace_parse) { 840 if (FLAG_trace_parse) {
837 timer.Start(); 841 timer.Start();
838 } 842 }
839 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone()); 843 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone());
840 844
841 // Initialize parser state. 845 // Initialize parser state.
842 CompleteParserRecorder recorder; 846 CompleteParserRecorder recorder;
843 847
844 if (produce_cached_parse_data()) { 848 if (produce_cached_parse_data()) {
845 log_ = &recorder; 849 log_ = &recorder;
846 } else if (consume_cached_parse_data()) { 850 } else if (consume_cached_parse_data()) {
847 cached_parse_data_->Initialize(); 851 cached_parse_data_->Initialize();
848 } 852 }
849 853
850 source = String::Flatten(source); 854 source = String::Flatten(source);
851 FunctionLiteral* result; 855 FunctionLiteral* result;
852 856
853 Scope* top_scope = NULL; 857 Scope* top_scope = NULL;
854 Scope* eval_scope = NULL; 858 Scope* eval_scope = NULL;
855 if (source->IsExternalTwoByteString()) { 859 if (source->IsExternalTwoByteString()) {
856 // Notice that the stream is destroyed at the end of the branch block. 860 // Notice that the stream is destroyed at the end of the branch block.
857 // The last line of the blocks can't be moved outside, even though they're 861 // The last line of the blocks can't be moved outside, even though they're
858 // identical calls. 862 // identical calls.
859 ExternalTwoByteStringUtf16CharacterStream stream( 863 ExternalTwoByteStringUtf16CharacterStream stream(
860 Handle<ExternalTwoByteString>::cast(source), 0, source->length()); 864 Handle<ExternalTwoByteString>::cast(source), 0, source->length());
861 scanner_.Initialize(&stream); 865 scanner_.Initialize(&stream);
862 result = DoParseProgram(info(), &top_scope, &eval_scope); 866 result = DoParseProgram(info, &top_scope, &eval_scope);
863 } else { 867 } else {
864 GenericStringUtf16CharacterStream stream(source, 0, source->length()); 868 GenericStringUtf16CharacterStream stream(source, 0, source->length());
865 scanner_.Initialize(&stream); 869 scanner_.Initialize(&stream);
866 result = DoParseProgram(info(), &top_scope, &eval_scope); 870 result = DoParseProgram(info, &top_scope, &eval_scope);
867 } 871 }
868 top_scope->set_end_position(source->length()); 872 top_scope->set_end_position(source->length());
869 if (eval_scope != NULL) { 873 if (eval_scope != NULL) {
870 eval_scope->set_end_position(source->length()); 874 eval_scope->set_end_position(source->length());
871 } 875 }
872 HandleSourceURLComments(); 876 HandleSourceURLComments(info);
873 877
874 if (FLAG_trace_parse && result != NULL) { 878 if (FLAG_trace_parse && result != NULL) {
875 double ms = timer.Elapsed().InMillisecondsF(); 879 double ms = timer.Elapsed().InMillisecondsF();
876 if (info()->is_eval()) { 880 if (info->is_eval()) {
877 PrintF("[parsing eval"); 881 PrintF("[parsing eval");
878 } else if (info()->script()->name()->IsString()) { 882 } else if (info->script()->name()->IsString()) {
879 String* name = String::cast(info()->script()->name()); 883 String* name = String::cast(info->script()->name());
880 SmartArrayPointer<char> name_chars = name->ToCString(); 884 SmartArrayPointer<char> name_chars = name->ToCString();
881 PrintF("[parsing script: %s", name_chars.get()); 885 PrintF("[parsing script: %s", name_chars.get());
882 } else { 886 } else {
883 PrintF("[parsing script"); 887 PrintF("[parsing script");
884 } 888 }
885 PrintF(" - took %0.3f ms]\n", ms); 889 PrintF(" - took %0.3f ms]\n", ms);
886 } 890 }
887 if (produce_cached_parse_data()) { 891 if (produce_cached_parse_data()) {
888 if (result != NULL) *info_->cached_data() = recorder.GetScriptData(); 892 if (result != NULL) *info->cached_data() = recorder.GetScriptData();
889 log_ = NULL; 893 log_ = NULL;
890 } 894 }
891 return result; 895 return result;
892 } 896 }
893 897
894 898
895 FunctionLiteral* Parser::DoParseProgram(CompilationInfo* info, Scope** scope, 899 FunctionLiteral* Parser::DoParseProgram(CompilationInfo* info, Scope** scope,
896 Scope** eval_scope) { 900 Scope** eval_scope) {
901 // Note that this function can be called from the main thread or from a
902 // background thread. We should not access anything Isolate / heap dependent
903 // via CompilationInfo, and also not pass it forward.
897 DCHECK(scope_ == NULL); 904 DCHECK(scope_ == NULL);
898 DCHECK(target_stack_ == NULL); 905 DCHECK(target_stack_ == NULL);
899 906
900 FunctionLiteral* result = NULL; 907 FunctionLiteral* result = NULL;
901 { 908 {
902 *scope = NewScope(scope_, SCRIPT_SCOPE); 909 *scope = NewScope(scope_, SCRIPT_SCOPE);
903 info->SetScriptScope(*scope); 910 info->SetScriptScope(*scope);
904 if (!info->context().is_null() && !info->context()->IsNativeContext()) { 911 if (!info->context().is_null() && !info->context()->IsNativeContext()) {
905 *scope = Scope::DeserializeScopeChain(info->isolate(), zone(), 912 *scope = Scope::DeserializeScopeChain(info->isolate(), zone(),
906 *info->context(), *scope); 913 *info->context(), *scope);
907 // The Scope is backed up by ScopeInfo (which is in the V8 heap); this 914 // The Scope is backed up by ScopeInfo (which is in the V8 heap); this
908 // means the Parser cannot operate independent of the V8 heap. Tell the 915 // means the Parser cannot operate independent of the V8 heap. Tell the
909 // string table to internalize strings and values right after they're 916 // string table to internalize strings and values right after they're
910 // created. 917 // created. This kind of parsing can only be done in the main thread.
rossberg 2015/02/12 10:31:29 Is there a way to DCHECK that here?
marja 2015/02/12 12:37:31 I added a bool parsing_on_main_thread_ which Parse
911 ast_value_factory()->Internalize(isolate()); 918 ast_value_factory()->Internalize(info->isolate());
912 } 919 }
913 original_scope_ = *scope; 920 original_scope_ = *scope;
914 if (info->is_eval()) { 921 if (info->is_eval()) {
915 if (!(*scope)->is_script_scope() || is_strict(info->language_mode())) { 922 if (!(*scope)->is_script_scope() || is_strict(info->language_mode())) {
916 *scope = NewScope(*scope, EVAL_SCOPE); 923 *scope = NewScope(*scope, EVAL_SCOPE);
917 } 924 }
918 } else if (info->is_global()) { 925 } else if (info->is_global()) {
919 *scope = NewScope(*scope, SCRIPT_SCOPE); 926 *scope = NewScope(*scope, SCRIPT_SCOPE);
920 } 927 }
921 (*scope)->set_start_position(0); 928 (*scope)->set_start_position(0);
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
978 } 985 }
979 } 986 }
980 987
981 // Make sure the target stack is empty. 988 // Make sure the target stack is empty.
982 DCHECK(target_stack_ == NULL); 989 DCHECK(target_stack_ == NULL);
983 990
984 return result; 991 return result;
985 } 992 }
986 993
987 994
988 FunctionLiteral* Parser::ParseLazy() { 995 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info) {
989 // It's OK to use the counters here, since this function is only called in 996 // It's OK to use the Isolate & counters here, since this function is only
990 // the main thread. 997 // called in the main thread.
991 HistogramTimerScope timer_scope(isolate()->counters()->parse_lazy()); 998 HistogramTimerScope timer_scope(info->isolate()->counters()->parse_lazy());
992 Handle<String> source(String::cast(script()->source())); 999 Handle<String> source(String::cast(info->script()->source()));
993 isolate()->counters()->total_parse_size()->Increment(source->length()); 1000 info->isolate()->counters()->total_parse_size()->Increment(source->length());
994 base::ElapsedTimer timer; 1001 base::ElapsedTimer timer;
995 if (FLAG_trace_parse) { 1002 if (FLAG_trace_parse) {
996 timer.Start(); 1003 timer.Start();
997 } 1004 }
998 Handle<SharedFunctionInfo> shared_info = info()->shared_info(); 1005 Handle<SharedFunctionInfo> shared_info = info->shared_info();
999 1006
1000 // Initialize parser state. 1007 // Initialize parser state.
1001 source = String::Flatten(source); 1008 source = String::Flatten(source);
1002 FunctionLiteral* result; 1009 FunctionLiteral* result;
1003 if (source->IsExternalTwoByteString()) { 1010 if (source->IsExternalTwoByteString()) {
1004 ExternalTwoByteStringUtf16CharacterStream stream( 1011 ExternalTwoByteStringUtf16CharacterStream stream(
1005 Handle<ExternalTwoByteString>::cast(source), 1012 Handle<ExternalTwoByteString>::cast(source),
1006 shared_info->start_position(), 1013 shared_info->start_position(),
1007 shared_info->end_position()); 1014 shared_info->end_position());
1008 result = ParseLazy(&stream); 1015 result = ParseLazy(info, &stream);
1009 } else { 1016 } else {
1010 GenericStringUtf16CharacterStream stream(source, 1017 GenericStringUtf16CharacterStream stream(source,
1011 shared_info->start_position(), 1018 shared_info->start_position(),
1012 shared_info->end_position()); 1019 shared_info->end_position());
1013 result = ParseLazy(&stream); 1020 result = ParseLazy(info, &stream);
1014 } 1021 }
1015 1022
1016 if (FLAG_trace_parse && result != NULL) { 1023 if (FLAG_trace_parse && result != NULL) {
1017 double ms = timer.Elapsed().InMillisecondsF(); 1024 double ms = timer.Elapsed().InMillisecondsF();
1018 SmartArrayPointer<char> name_chars = result->debug_name()->ToCString(); 1025 SmartArrayPointer<char> name_chars = result->debug_name()->ToCString();
1019 PrintF("[parsing function: %s - took %0.3f ms]\n", name_chars.get(), ms); 1026 PrintF("[parsing function: %s - took %0.3f ms]\n", name_chars.get(), ms);
1020 } 1027 }
1021 return result; 1028 return result;
1022 } 1029 }
1023 1030
1024 1031
1025 FunctionLiteral* Parser::ParseLazy(Utf16CharacterStream* source) { 1032 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info,
1026 Handle<SharedFunctionInfo> shared_info = info()->shared_info(); 1033 Utf16CharacterStream* source) {
1034 Handle<SharedFunctionInfo> shared_info = info->shared_info();
1027 scanner_.Initialize(source); 1035 scanner_.Initialize(source);
1028 DCHECK(scope_ == NULL); 1036 DCHECK(scope_ == NULL);
1029 DCHECK(target_stack_ == NULL); 1037 DCHECK(target_stack_ == NULL);
1030 1038
1031 Handle<String> name(String::cast(shared_info->name())); 1039 Handle<String> name(String::cast(shared_info->name()));
1032 DCHECK(ast_value_factory()); 1040 DCHECK(ast_value_factory());
1033 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone()); 1041 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone());
1034 const AstRawString* raw_name = ast_value_factory()->GetString(name); 1042 const AstRawString* raw_name = ast_value_factory()->GetString(name);
1035 fni_->PushEnclosingName(raw_name); 1043 fni_->PushEnclosingName(raw_name);
1036 1044
1037 ParsingModeScope parsing_mode(this, PARSE_EAGERLY); 1045 ParsingModeScope parsing_mode(this, PARSE_EAGERLY);
1038 1046
1039 // Place holder for the result. 1047 // Place holder for the result.
1040 FunctionLiteral* result = NULL; 1048 FunctionLiteral* result = NULL;
1041 1049
1042 { 1050 {
1043 // Parse the function literal. 1051 // Parse the function literal.
1044 Scope* scope = NewScope(scope_, SCRIPT_SCOPE); 1052 Scope* scope = NewScope(scope_, SCRIPT_SCOPE);
1045 info()->SetScriptScope(scope); 1053 info->SetScriptScope(scope);
1046 if (!info()->closure().is_null()) { 1054 if (!info->closure().is_null()) {
1047 scope = Scope::DeserializeScopeChain(isolate(), zone(), 1055 // Ok to use Isolate here, since lazy function parsing is only done in the
1048 info()->closure()->context(), scope); 1056 // main thread.
1057 scope = Scope::DeserializeScopeChain(info->isolate(), zone(),
1058 info->closure()->context(), scope);
1049 } 1059 }
1050 original_scope_ = scope; 1060 original_scope_ = scope;
1051 AstNodeFactory function_factory(ast_value_factory()); 1061 AstNodeFactory function_factory(ast_value_factory());
1052 FunctionState function_state(&function_state_, &scope_, scope, 1062 FunctionState function_state(&function_state_, &scope_, scope,
1053 shared_info->kind(), &function_factory); 1063 shared_info->kind(), &function_factory);
1054 DCHECK(is_sloppy(scope->language_mode()) || 1064 DCHECK(is_sloppy(scope->language_mode()) ||
1055 is_strict(info()->language_mode())); 1065 is_strict(info->language_mode()));
1056 DCHECK(info()->language_mode() == shared_info->language_mode()); 1066 DCHECK(info->language_mode() == shared_info->language_mode());
1057 scope->SetLanguageMode(shared_info->language_mode()); 1067 scope->SetLanguageMode(shared_info->language_mode());
1058 FunctionLiteral::FunctionType function_type = shared_info->is_expression() 1068 FunctionLiteral::FunctionType function_type = shared_info->is_expression()
1059 ? (shared_info->is_anonymous() 1069 ? (shared_info->is_anonymous()
1060 ? FunctionLiteral::ANONYMOUS_EXPRESSION 1070 ? FunctionLiteral::ANONYMOUS_EXPRESSION
1061 : FunctionLiteral::NAMED_EXPRESSION) 1071 : FunctionLiteral::NAMED_EXPRESSION)
1062 : FunctionLiteral::DECLARATION; 1072 : FunctionLiteral::DECLARATION;
1063 bool ok = true; 1073 bool ok = true;
1064 1074
1065 if (shared_info->is_arrow()) { 1075 if (shared_info->is_arrow()) {
1066 // The first expression being parsed is the parameter list of the arrow 1076 // The first expression being parsed is the parameter list of the arrow
(...skipping 2918 matching lines...) Expand 10 before | Expand all | Expand 10 after
3985 PreParser::PreParseResult Parser::ParseLazyFunctionBodyWithPreParser( 3995 PreParser::PreParseResult Parser::ParseLazyFunctionBodyWithPreParser(
3986 SingletonLogger* logger) { 3996 SingletonLogger* logger) {
3987 // This function may be called on a background thread too; record only the 3997 // This function may be called on a background thread too; record only the
3988 // main thread preparse times. 3998 // main thread preparse times.
3989 if (pre_parse_timer_ != NULL) { 3999 if (pre_parse_timer_ != NULL) {
3990 pre_parse_timer_->Start(); 4000 pre_parse_timer_->Start();
3991 } 4001 }
3992 DCHECK_EQ(Token::LBRACE, scanner()->current_token()); 4002 DCHECK_EQ(Token::LBRACE, scanner()->current_token());
3993 4003
3994 if (reusable_preparser_ == NULL) { 4004 if (reusable_preparser_ == NULL) {
3995 reusable_preparser_ = new PreParser( 4005 reusable_preparser_ = new PreParser(zone(), &scanner_, ast_value_factory(),
3996 isolate(), zone(), &scanner_, ast_value_factory(), NULL, stack_limit_); 4006 NULL, stack_limit_);
3997 reusable_preparser_->set_allow_lazy(true); 4007 reusable_preparser_->set_allow_lazy(true);
3998 reusable_preparser_->set_allow_natives(allow_natives()); 4008 reusable_preparser_->set_allow_natives(allow_natives());
3999 reusable_preparser_->set_allow_harmony_scoping(allow_harmony_scoping()); 4009 reusable_preparser_->set_allow_harmony_scoping(allow_harmony_scoping());
4000 reusable_preparser_->set_allow_harmony_modules(allow_harmony_modules()); 4010 reusable_preparser_->set_allow_harmony_modules(allow_harmony_modules());
4001 reusable_preparser_->set_allow_harmony_arrow_functions( 4011 reusable_preparser_->set_allow_harmony_arrow_functions(
4002 allow_harmony_arrow_functions()); 4012 allow_harmony_arrow_functions());
4003 reusable_preparser_->set_allow_harmony_numeric_literals( 4013 reusable_preparser_->set_allow_harmony_numeric_literals(
4004 allow_harmony_numeric_literals()); 4014 allow_harmony_numeric_literals());
4005 reusable_preparser_->set_allow_harmony_classes(allow_harmony_classes()); 4015 reusable_preparser_->set_allow_harmony_classes(allow_harmony_classes());
4006 reusable_preparser_->set_allow_harmony_object_literals( 4016 reusable_preparser_->set_allow_harmony_object_literals(
(...skipping 219 matching lines...) Expand 10 before | Expand all | Expand 10 after
4226 4236
4227 DCHECK(stat->is_target_for_anonymous()); 4237 DCHECK(stat->is_target_for_anonymous());
4228 if (anonymous || ContainsLabel(stat->labels(), label)) { 4238 if (anonymous || ContainsLabel(stat->labels(), label)) {
4229 return stat; 4239 return stat;
4230 } 4240 }
4231 } 4241 }
4232 return NULL; 4242 return NULL;
4233 } 4243 }
4234 4244
4235 4245
4236 void Parser::HandleSourceURLComments() { 4246 void Parser::HandleSourceURLComments(CompilationInfo* info) {
4237 if (scanner_.source_url()->length() > 0) { 4247 if (scanner_.source_url()->length() > 0) {
4238 Handle<String> source_url = scanner_.source_url()->Internalize(isolate()); 4248 Handle<String> source_url =
4239 info_->script()->set_source_url(*source_url); 4249 scanner_.source_url()->Internalize(info->isolate());
4250 info->script()->set_source_url(*source_url);
4240 } 4251 }
4241 if (scanner_.source_mapping_url()->length() > 0) { 4252 if (scanner_.source_mapping_url()->length() > 0) {
4242 Handle<String> source_mapping_url = 4253 Handle<String> source_mapping_url =
4243 scanner_.source_mapping_url()->Internalize(isolate()); 4254 scanner_.source_mapping_url()->Internalize(info->isolate());
4244 info_->script()->set_source_mapping_url(*source_mapping_url); 4255 info->script()->set_source_mapping_url(*source_mapping_url);
4245 } 4256 }
4246 } 4257 }
4247 4258
4248 4259
4249 void Parser::ThrowPendingError() { 4260 void Parser::ThrowPendingError(Isolate* isolate, Handle<Script> script) {
4250 DCHECK(ast_value_factory()->IsInternalized()); 4261 DCHECK(ast_value_factory()->IsInternalized());
4251 if (has_pending_error_) { 4262 if (has_pending_error_) {
4252 MessageLocation location(script(), pending_error_location_.beg_pos, 4263 MessageLocation location(script, pending_error_location_.beg_pos,
4253 pending_error_location_.end_pos); 4264 pending_error_location_.end_pos);
4254 Factory* factory = isolate()->factory(); 4265 Factory* factory = isolate->factory();
4255 bool has_arg = 4266 bool has_arg =
4256 pending_error_arg_ != NULL || pending_error_char_arg_ != NULL; 4267 pending_error_arg_ != NULL || pending_error_char_arg_ != NULL;
4257 Handle<FixedArray> elements = factory->NewFixedArray(has_arg ? 1 : 0); 4268 Handle<FixedArray> elements = factory->NewFixedArray(has_arg ? 1 : 0);
4258 if (pending_error_arg_ != NULL) { 4269 if (pending_error_arg_ != NULL) {
4259 Handle<String> arg_string = pending_error_arg_->string(); 4270 Handle<String> arg_string = pending_error_arg_->string();
4260 elements->set(0, *arg_string); 4271 elements->set(0, *arg_string);
4261 } else if (pending_error_char_arg_ != NULL) { 4272 } else if (pending_error_char_arg_ != NULL) {
4262 Handle<String> arg_string = 4273 Handle<String> arg_string =
4263 factory->NewStringFromUtf8(CStrVector(pending_error_char_arg_)) 4274 factory->NewStringFromUtf8(CStrVector(pending_error_char_arg_))
4264 .ToHandleChecked(); 4275 .ToHandleChecked();
4265 elements->set(0, *arg_string); 4276 elements->set(0, *arg_string);
4266 } 4277 }
4267 isolate()->debug()->OnCompileError(script()); 4278 isolate->debug()->OnCompileError(script);
4268 4279
4269 Handle<JSArray> array = factory->NewJSArrayWithElements(elements); 4280 Handle<JSArray> array = factory->NewJSArrayWithElements(elements);
4270 Handle<Object> error; 4281 Handle<Object> error;
4271 MaybeHandle<Object> maybe_error = 4282 MaybeHandle<Object> maybe_error =
4272 pending_error_is_reference_error_ 4283 pending_error_is_reference_error_
4273 ? factory->NewReferenceError(pending_error_message_, array) 4284 ? factory->NewReferenceError(pending_error_message_, array)
4274 : factory->NewSyntaxError(pending_error_message_, array); 4285 : factory->NewSyntaxError(pending_error_message_, array);
4275 4286
4276 if (maybe_error.ToHandle(&error)) { 4287 if (maybe_error.ToHandle(&error)) {
4277 Handle<JSObject> jserror = Handle<JSObject>::cast(error); 4288 Handle<JSObject> jserror = Handle<JSObject>::cast(error);
4278 4289
4279 Handle<Name> key_start_pos = factory->error_start_pos_symbol(); 4290 Handle<Name> key_start_pos = factory->error_start_pos_symbol();
4280 JSObject::SetProperty( 4291 JSObject::SetProperty(jserror, key_start_pos,
4281 jserror, key_start_pos, 4292 handle(Smi::FromInt(location.start_pos()), isolate),
4282 handle(Smi::FromInt(location.start_pos()), isolate()), 4293 SLOPPY).Check();
4283 SLOPPY).Check();
4284 4294
4285 Handle<Name> key_end_pos = factory->error_end_pos_symbol(); 4295 Handle<Name> key_end_pos = factory->error_end_pos_symbol();
4286 JSObject::SetProperty(jserror, key_end_pos, 4296 JSObject::SetProperty(jserror, key_end_pos,
4287 handle(Smi::FromInt(location.end_pos()), isolate()), 4297 handle(Smi::FromInt(location.end_pos()), isolate),
4288 SLOPPY).Check(); 4298 SLOPPY).Check();
4289 4299
4290 Handle<Name> key_script = factory->error_script_symbol(); 4300 Handle<Name> key_script = factory->error_script_symbol();
4291 JSObject::SetProperty(jserror, key_script, script(), SLOPPY).Check(); 4301 JSObject::SetProperty(jserror, key_script, script, SLOPPY).Check();
4292 4302
4293 isolate()->Throw(*error, &location); 4303 isolate->Throw(*error, &location);
4294 } 4304 }
4295 } 4305 }
4296 } 4306 }
4297 4307
4298 4308
4299 void Parser::Internalize() { 4309 void Parser::Internalize(CompilationInfo* info) {
4300 // Internalize strings. 4310 // Internalize strings.
4301 ast_value_factory()->Internalize(isolate()); 4311 ast_value_factory()->Internalize(info->isolate());
4302 4312
4303 // Error processing. 4313 // Error processing.
4304 if (info()->function() == NULL) { 4314 if (info->function() == NULL) {
4305 if (stack_overflow()) { 4315 if (stack_overflow()) {
4306 isolate()->StackOverflow(); 4316 info->isolate()->StackOverflow();
4307 } else { 4317 } else {
4308 ThrowPendingError(); 4318 ThrowPendingError(info->isolate(), info->script());
4309 } 4319 }
4310 } 4320 }
4311 4321
4312 // Move statistics to Isolate. 4322 // Move statistics to Isolate.
4313 for (int feature = 0; feature < v8::Isolate::kUseCounterFeatureCount; 4323 for (int feature = 0; feature < v8::Isolate::kUseCounterFeatureCount;
4314 ++feature) { 4324 ++feature) {
4315 for (int i = 0; i < use_counts_[feature]; ++i) { 4325 for (int i = 0; i < use_counts_[feature]; ++i) {
4316 isolate()->CountUsage(v8::Isolate::UseCounterFeature(feature)); 4326 info->isolate()->CountUsage(v8::Isolate::UseCounterFeature(feature));
4317 } 4327 }
4318 } 4328 }
4319 isolate()->counters()->total_preparse_skipped()->Increment( 4329 info->isolate()->counters()->total_preparse_skipped()->Increment(
4320 total_preparse_skipped_); 4330 total_preparse_skipped_);
4321 } 4331 }
4322 4332
4323 4333
4324 // ---------------------------------------------------------------------------- 4334 // ----------------------------------------------------------------------------
4325 // Regular expressions 4335 // Regular expressions
4326 4336
4327 4337
4328 RegExpParser::RegExpParser(FlatStringReader* in, Handle<String>* error, 4338 RegExpParser::RegExpParser(FlatStringReader* in, Handle<String>* error,
4329 bool multiline, bool unicode, Isolate* isolate, 4339 bool multiline, bool unicode, Isolate* isolate,
(...skipping 897 matching lines...) Expand 10 before | Expand all | Expand 10 after
5227 result->tree = tree; 5237 result->tree = tree;
5228 int capture_count = parser.captures_started(); 5238 int capture_count = parser.captures_started();
5229 result->simple = tree->IsAtom() && parser.simple() && capture_count == 0; 5239 result->simple = tree->IsAtom() && parser.simple() && capture_count == 0;
5230 result->contains_anchor = parser.contains_anchor(); 5240 result->contains_anchor = parser.contains_anchor();
5231 result->capture_count = capture_count; 5241 result->capture_count = capture_count;
5232 } 5242 }
5233 return !parser.failed(); 5243 return !parser.failed();
5234 } 5244 }
5235 5245
5236 5246
5237 bool Parser::Parse() { 5247 bool Parser::ParseOnMainThread(CompilationInfo* info) {
5238 DCHECK(info()->function() == NULL); 5248 DCHECK(info->function() == NULL);
5239 FunctionLiteral* result = NULL; 5249 FunctionLiteral* result = NULL;
5240 pre_parse_timer_ = isolate()->counters()->pre_parse(); 5250 // Ok to use Isolate here; this function is only called in the main thread.
5251 Isolate* isolate = info->isolate();
5252 pre_parse_timer_ = isolate->counters()->pre_parse();
5241 if (FLAG_trace_parse || allow_natives() || extension_ != NULL) { 5253 if (FLAG_trace_parse || allow_natives() || extension_ != NULL) {
5242 // If intrinsics are allowed, the Parser cannot operate independent of the 5254 // If intrinsics are allowed, the Parser cannot operate independent of the
5243 // V8 heap because of Runtime. Tell the string table to internalize strings 5255 // V8 heap because of Runtime. Tell the string table to internalize strings
5244 // and values right after they're created. 5256 // and values right after they're created.
5245 ast_value_factory()->Internalize(isolate()); 5257 ast_value_factory()->Internalize(isolate);
5246 } 5258 }
5247 5259
5248 if (info()->is_lazy()) { 5260 if (info->is_lazy()) {
5249 DCHECK(!info()->is_eval()); 5261 DCHECK(!info->is_eval());
5250 if (info()->shared_info()->is_function()) { 5262 if (info->shared_info()->is_function()) {
5251 result = ParseLazy(); 5263 result = ParseLazy(info);
5252 } else { 5264 } else {
5253 result = ParseProgram(); 5265 result = ParseProgram(info);
5254 } 5266 }
5255 } else { 5267 } else {
5256 SetCachedData(); 5268 SetCachedData(info);
5257 result = ParseProgram(); 5269 result = ParseProgram(info);
5258 } 5270 }
5259 info()->SetFunction(result); 5271 info->SetFunction(result);
5260 5272
5261 Internalize(); 5273 Internalize(info);
5262 DCHECK(ast_value_factory()->IsInternalized()); 5274 DCHECK(ast_value_factory()->IsInternalized());
5263 return (result != NULL); 5275 return (result != NULL);
5264 } 5276 }
5265 5277
5266 5278
5267 void Parser::ParseOnBackground() { 5279 void Parser::ParseOnBackground(CompilationInfo* info) {
5268 DCHECK(info()->function() == NULL); 5280 DCHECK(info->function() == NULL);
5269 FunctionLiteral* result = NULL; 5281 FunctionLiteral* result = NULL;
5270 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone()); 5282 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone());
5271 5283
5272 CompleteParserRecorder recorder; 5284 CompleteParserRecorder recorder;
5273 if (produce_cached_parse_data()) log_ = &recorder; 5285 if (produce_cached_parse_data()) log_ = &recorder;
5274 5286
5275 DCHECK(info()->source_stream() != NULL); 5287 DCHECK(info->source_stream() != NULL);
5276 ExternalStreamingStream stream(info()->source_stream(), 5288 ExternalStreamingStream stream(info->source_stream(),
5277 info()->source_stream_encoding()); 5289 info->source_stream_encoding());
5278 scanner_.Initialize(&stream); 5290 scanner_.Initialize(&stream);
5279 DCHECK(info()->context().is_null() || info()->context()->IsNativeContext()); 5291 DCHECK(info->context().is_null() || info->context()->IsNativeContext());
5280 5292
5281 // When streaming, we don't know the length of the source until we have parsed 5293 // When streaming, we don't know the length of the source until we have parsed
5282 // it. The raw data can be UTF-8, so we wouldn't know the source length until 5294 // it. The raw data can be UTF-8, so we wouldn't know the source length until
5283 // we have decoded it anyway even if we knew the raw data length (which we 5295 // we have decoded it anyway even if we knew the raw data length (which we
5284 // don't). We work around this by storing all the scopes which need their end 5296 // don't). We work around this by storing all the scopes which need their end
5285 // position set at the end of the script (the top scope and possible eval 5297 // position set at the end of the script (the top scope and possible eval
5286 // scopes) and set their end position after we know the script length. 5298 // scopes) and set their end position after we know the script length.
5287 Scope* top_scope = NULL; 5299 Scope* top_scope = NULL;
5288 Scope* eval_scope = NULL; 5300 Scope* eval_scope = NULL;
5289 result = DoParseProgram(info(), &top_scope, &eval_scope); 5301 result = DoParseProgram(info, &top_scope, &eval_scope);
5290 5302
5291 top_scope->set_end_position(scanner()->location().end_pos); 5303 top_scope->set_end_position(scanner()->location().end_pos);
5292 if (eval_scope != NULL) { 5304 if (eval_scope != NULL) {
5293 eval_scope->set_end_position(scanner()->location().end_pos); 5305 eval_scope->set_end_position(scanner()->location().end_pos);
5294 } 5306 }
5295 5307
5296 info()->SetFunction(result); 5308 info->SetFunction(result);
5297 5309
5298 // We cannot internalize on a background thread; a foreground task will take 5310 // We cannot internalize on a background thread; a foreground task will take
5299 // care of calling Parser::Internalize just before compilation. 5311 // care of calling Parser::Internalize just before compilation.
5300 5312
5301 if (produce_cached_parse_data()) { 5313 if (produce_cached_parse_data()) {
5302 if (result != NULL) *info_->cached_data() = recorder.GetScriptData(); 5314 if (result != NULL) *info->cached_data() = recorder.GetScriptData();
5303 log_ = NULL; 5315 log_ = NULL;
5304 } 5316 }
5305 } 5317 }
5306 5318
5307 5319
5308 ParserTraits::TemplateLiteralState Parser::OpenTemplateLiteral(int pos) { 5320 ParserTraits::TemplateLiteralState Parser::OpenTemplateLiteral(int pos) {
5309 return new (zone()) ParserTraits::TemplateLiteral(zone(), pos); 5321 return new (zone()) ParserTraits::TemplateLiteral(zone(), pos);
5310 } 5322 }
5311 5323
5312 5324
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
5419 } else { 5431 } else {
5420 const uc16* data = reinterpret_cast<const uc16*>(raw_string->raw_data()); 5432 const uc16* data = reinterpret_cast<const uc16*>(raw_string->raw_data());
5421 running_hash = StringHasher::ComputeRunningHash(running_hash, data, 5433 running_hash = StringHasher::ComputeRunningHash(running_hash, data,
5422 raw_string->length()); 5434 raw_string->length());
5423 } 5435 }
5424 } 5436 }
5425 5437
5426 return running_hash; 5438 return running_hash;
5427 } 5439 }
5428 } } // namespace v8::internal 5440 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/parser.h ('k') | src/preparser.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698