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

Side by Side Diff: src/parsing/parser.cc

Issue 2474393003: [parser] Give preparser and parser independent loggers (Closed)
Patch Set: Addressed comment Created 4 years, 1 month 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/parsing/parser.h ('k') | src/parsing/parser-base.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/parsing/parser.h" 5 #include "src/parsing/parser.h"
6 6
7 #include <memory> 7 #include <memory>
8 8
9 #include "src/api.h" 9 #include "src/api.h"
10 #include "src/ast/ast-expression-rewriter.h" 10 #include "src/ast/ast-expression-rewriter.h"
(...skipping 568 matching lines...) Expand 10 before | Expand all | Expand 10 after
579 ReportMessage(MessageTemplate::kNotDefined, name); 579 ReportMessage(MessageTemplate::kNotDefined, name);
580 *ok = false; 580 *ok = false;
581 return nullptr; 581 return nullptr;
582 } 582 }
583 583
584 return factory()->NewCallRuntime(context_index, args, pos); 584 return factory()->NewCallRuntime(context_index, args, pos);
585 } 585 }
586 586
587 Parser::Parser(ParseInfo* info) 587 Parser::Parser(ParseInfo* info)
588 : ParserBase<Parser>(info->zone(), &scanner_, info->stack_limit(), 588 : ParserBase<Parser>(info->zone(), &scanner_, info->stack_limit(),
589 info->extension(), info->ast_value_factory(), NULL), 589 info->extension(), info->ast_value_factory()),
590 scanner_(info->unicode_cache()), 590 scanner_(info->unicode_cache()),
591 reusable_preparser_(NULL), 591 reusable_preparser_(nullptr),
592 original_scope_(NULL), 592 original_scope_(nullptr),
593 target_stack_(NULL), 593 target_stack_(nullptr),
594 compile_options_(info->compile_options()), 594 compile_options_(info->compile_options()),
595 cached_parse_data_(nullptr), 595 cached_parse_data_(nullptr),
596 total_preparse_skipped_(0), 596 total_preparse_skipped_(0),
597 parsing_on_main_thread_(true) { 597 parsing_on_main_thread_(true),
598 log_(nullptr) {
598 // Even though we were passed ParseInfo, we should not store it in 599 // Even though we were passed ParseInfo, we should not store it in
599 // Parser - this makes sure that Isolate is not accidentally accessed via 600 // Parser - this makes sure that Isolate is not accidentally accessed via
600 // ParseInfo during background parsing. 601 // ParseInfo during background parsing.
601 DCHECK(!info->script().is_null() || info->source_stream() != nullptr || 602 DCHECK(!info->script().is_null() || info->source_stream() != nullptr ||
602 info->character_stream() != nullptr); 603 info->character_stream() != nullptr);
603 // Determine if functions can be lazily compiled. This is necessary to 604 // Determine if functions can be lazily compiled. This is necessary to
604 // allow some of our builtin JS files to be lazily compiled. These 605 // allow some of our builtin JS files to be lazily compiled. These
605 // builtins cannot be handled lazily by the parser, since we have to know 606 // builtins cannot be handled lazily by the parser, since we have to know
606 // if a function uses the special natives syntax, which is something the 607 // if a function uses the special natives syntax, which is something the
607 // parser records. 608 // parser records.
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
674 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("v8.compile"), "V8.ParseProgram"); 675 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("v8.compile"), "V8.ParseProgram");
675 Handle<String> source(String::cast(info->script()->source())); 676 Handle<String> source(String::cast(info->script()->source()));
676 isolate->counters()->total_parse_size()->Increment(source->length()); 677 isolate->counters()->total_parse_size()->Increment(source->length());
677 base::ElapsedTimer timer; 678 base::ElapsedTimer timer;
678 if (FLAG_trace_parse) { 679 if (FLAG_trace_parse) {
679 timer.Start(); 680 timer.Start();
680 } 681 }
681 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone()); 682 fni_ = new (zone()) FuncNameInferrer(ast_value_factory(), zone());
682 683
683 // Initialize parser state. 684 // Initialize parser state.
684 CompleteParserRecorder recorder; 685 ParserLogger logger;
685 686
686 if (produce_cached_parse_data()) { 687 if (produce_cached_parse_data()) {
687 log_ = &recorder; 688 log_ = &logger;
688 } else if (consume_cached_parse_data()) { 689 } else if (consume_cached_parse_data()) {
689 cached_parse_data_->Initialize(); 690 cached_parse_data_->Initialize();
690 } 691 }
691 692
692 DeserializeScopeChain(info, info->maybe_outer_scope_info()); 693 DeserializeScopeChain(info, info->maybe_outer_scope_info());
693 694
694 source = String::Flatten(source); 695 source = String::Flatten(source);
695 FunctionLiteral* result; 696 FunctionLiteral* result;
696 697
697 { 698 {
698 std::unique_ptr<Utf16CharacterStream> stream(ScannerStream::For(source)); 699 std::unique_ptr<Utf16CharacterStream> stream(ScannerStream::For(source));
699 scanner_.Initialize(stream.get()); 700 scanner_.Initialize(stream.get());
700 result = DoParseProgram(info); 701 result = DoParseProgram(info);
701 } 702 }
702 if (result != NULL) { 703 if (result != NULL) {
703 DCHECK_EQ(scanner_.peek_location().beg_pos, source->length()); 704 DCHECK_EQ(scanner_.peek_location().beg_pos, source->length());
704 } 705 }
705 HandleSourceURLComments(isolate, info->script()); 706 HandleSourceURLComments(isolate, info->script());
706 707
707 if (FLAG_trace_parse && result != NULL) { 708 if (FLAG_trace_parse && result != nullptr) {
708 double ms = timer.Elapsed().InMillisecondsF(); 709 double ms = timer.Elapsed().InMillisecondsF();
709 if (info->is_eval()) { 710 if (info->is_eval()) {
710 PrintF("[parsing eval"); 711 PrintF("[parsing eval");
711 } else if (info->script()->name()->IsString()) { 712 } else if (info->script()->name()->IsString()) {
712 String* name = String::cast(info->script()->name()); 713 String* name = String::cast(info->script()->name());
713 std::unique_ptr<char[]> name_chars = name->ToCString(); 714 std::unique_ptr<char[]> name_chars = name->ToCString();
714 PrintF("[parsing script: %s", name_chars.get()); 715 PrintF("[parsing script: %s", name_chars.get());
715 } else { 716 } else {
716 PrintF("[parsing script"); 717 PrintF("[parsing script");
717 } 718 }
718 PrintF(" - took %0.3f ms]\n", ms); 719 PrintF(" - took %0.3f ms]\n", ms);
719 } 720 }
720 if (produce_cached_parse_data()) { 721 if (produce_cached_parse_data() && result != nullptr) {
721 if (result != NULL) *info->cached_data() = recorder.GetScriptData(); 722 *info->cached_data() = logger.GetScriptData();
722 log_ = NULL;
723 } 723 }
724 log_ = nullptr;
724 return result; 725 return result;
725 } 726 }
726 727
727 728
728 FunctionLiteral* Parser::DoParseProgram(ParseInfo* info) { 729 FunctionLiteral* Parser::DoParseProgram(ParseInfo* info) {
729 // Note that this function can be called from the main thread or from a 730 // Note that this function can be called from the main thread or from a
730 // background thread. We should not access anything Isolate / heap dependent 731 // background thread. We should not access anything Isolate / heap dependent
731 // via ParseInfo, and also not pass it forward. 732 // via ParseInfo, and also not pass it forward.
732 DCHECK_NULL(scope_state_); 733 DCHECK_NULL(scope_state_);
733 DCHECK_NULL(target_stack_); 734 DCHECK_NULL(target_stack_);
(...skipping 2035 matching lines...) Expand 10 before | Expand all | Expand 10 after
2769 SetLanguageMode(function_scope, entry.language_mode()); 2770 SetLanguageMode(function_scope, entry.language_mode());
2770 if (entry.uses_super_property()) 2771 if (entry.uses_super_property())
2771 function_scope->RecordSuperPropertyUsage(); 2772 function_scope->RecordSuperPropertyUsage();
2772 if (entry.calls_eval()) function_scope->RecordEvalCall(); 2773 if (entry.calls_eval()) function_scope->RecordEvalCall();
2773 return kLazyParsingComplete; 2774 return kLazyParsingComplete;
2774 } 2775 }
2775 cached_parse_data_->Reject(); 2776 cached_parse_data_->Reject();
2776 } 2777 }
2777 // With no cached data, we partially parse the function, without building an 2778 // With no cached data, we partially parse the function, without building an
2778 // AST. This gathers the data needed to build a lazy function. 2779 // AST. This gathers the data needed to build a lazy function.
2779 SingletonLogger logger;
2780 PreParser::PreParseResult result = ParseFunctionWithPreParser( 2780 PreParser::PreParseResult result = ParseFunctionWithPreParser(
2781 kind, function_scope, &logger, is_inner_function, may_abort); 2781 kind, function_scope, is_inner_function, may_abort);
2782 2782
2783 // Return immediately if pre-parser decided to abort parsing. 2783 // Return immediately if pre-parser decided to abort parsing.
2784 if (result == PreParser::kPreParseAbort) return kLazyParsingAborted; 2784 if (result == PreParser::kPreParseAbort) return kLazyParsingAborted;
2785 if (result == PreParser::kPreParseStackOverflow) { 2785 if (result == PreParser::kPreParseStackOverflow) {
2786 // Propagate stack overflow. 2786 // Propagate stack overflow.
2787 set_stack_overflow(); 2787 set_stack_overflow();
2788 *ok = false; 2788 *ok = false;
2789 return kLazyParsingComplete; 2789 return kLazyParsingComplete;
2790 } 2790 }
2791 if (logger.has_error()) { 2791 PreParserLogger* logger = reusable_preparser_->logger();
2792 ReportMessageAt(Scanner::Location(logger.start(), logger.end()), 2792 if (logger->has_error()) {
2793 logger.message(), logger.argument_opt(), 2793 ReportMessageAt(Scanner::Location(logger->start(), logger->end()),
2794 logger.error_type()); 2794 logger->message(), logger->argument_opt(),
2795 logger->error_type());
2795 *ok = false; 2796 *ok = false;
2796 return kLazyParsingComplete; 2797 return kLazyParsingComplete;
2797 } 2798 }
2798 function_scope->set_end_position(logger.end()); 2799 function_scope->set_end_position(logger->end());
2799 Expect(Token::RBRACE, CHECK_OK_VALUE(kLazyParsingComplete)); 2800 Expect(Token::RBRACE, CHECK_OK_VALUE(kLazyParsingComplete));
2800 total_preparse_skipped_ += 2801 total_preparse_skipped_ +=
2801 function_scope->end_position() - function_scope->start_position(); 2802 function_scope->end_position() - function_scope->start_position();
2802 *num_parameters = logger.num_parameters(); 2803 *num_parameters = logger->num_parameters();
2803 *function_length = logger.function_length(); 2804 *function_length = logger->function_length();
2804 *has_duplicate_parameters = logger.has_duplicate_parameters(); 2805 *has_duplicate_parameters = logger->has_duplicate_parameters();
2805 *materialized_literal_count = logger.literals(); 2806 *materialized_literal_count = logger->literals();
2806 *expected_property_count = logger.properties(); 2807 *expected_property_count = logger->properties();
2807 SetLanguageMode(function_scope, logger.language_mode());
2808 if (logger.uses_super_property()) function_scope->RecordSuperPropertyUsage();
2809 if (logger.calls_eval()) function_scope->RecordEvalCall();
2810 if (!is_inner_function && produce_cached_parse_data()) { 2808 if (!is_inner_function && produce_cached_parse_data()) {
2811 DCHECK(log_); 2809 DCHECK(log_);
2812 log_->LogFunction( 2810 log_->LogFunction(
2813 function_scope->start_position(), function_scope->end_position(), 2811 function_scope->start_position(), function_scope->end_position(),
2814 *num_parameters, *function_length, *has_duplicate_parameters, 2812 *num_parameters, *function_length, *has_duplicate_parameters,
2815 *materialized_literal_count, *expected_property_count, language_mode(), 2813 *materialized_literal_count, *expected_property_count, language_mode(),
2816 function_scope->uses_super_property(), function_scope->calls_eval()); 2814 function_scope->uses_super_property(), function_scope->calls_eval());
2817 } 2815 }
2818 return kLazyParsingComplete; 2816 return kLazyParsingComplete;
2819 } 2817 }
(...skipping 462 matching lines...) Expand 10 before | Expand all | Expand 10 after
3282 statement = factory()->NewEmptyStatement(kNoSourcePosition); 3280 statement = factory()->NewEmptyStatement(kNoSourcePosition);
3283 } 3281 }
3284 result->Set(kFunctionNameAssignmentIndex, statement); 3282 result->Set(kFunctionNameAssignmentIndex, statement);
3285 } 3283 }
3286 3284
3287 MarkCollectedTailCallExpressions(); 3285 MarkCollectedTailCallExpressions();
3288 return result; 3286 return result;
3289 } 3287 }
3290 3288
3291 PreParser::PreParseResult Parser::ParseFunctionWithPreParser( 3289 PreParser::PreParseResult Parser::ParseFunctionWithPreParser(
3292 FunctionKind kind, DeclarationScope* function_scope, 3290 FunctionKind kind, DeclarationScope* function_scope, bool is_inner_function,
3293 SingletonLogger* logger, bool is_inner_function, bool may_abort) { 3291 bool may_abort) {
3294 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("v8.compile"), "V8.PreParse"); 3292 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("v8.compile"), "V8.PreParse");
3295 3293
3296 if (reusable_preparser_ == NULL) { 3294 if (reusable_preparser_ == NULL) {
3297 reusable_preparser_ = new PreParser(zone(), &scanner_, ast_value_factory(), 3295 reusable_preparser_ =
3298 NULL, stack_limit_); 3296 new PreParser(zone(), &scanner_, ast_value_factory(), stack_limit_);
3299 reusable_preparser_->set_allow_lazy(true); 3297 reusable_preparser_->set_allow_lazy(true);
3300 #define SET_ALLOW(name) reusable_preparser_->set_allow_##name(allow_##name()); 3298 #define SET_ALLOW(name) reusable_preparser_->set_allow_##name(allow_##name());
3301 SET_ALLOW(natives); 3299 SET_ALLOW(natives);
3302 SET_ALLOW(harmony_do_expressions); 3300 SET_ALLOW(harmony_do_expressions);
3303 SET_ALLOW(harmony_function_sent); 3301 SET_ALLOW(harmony_function_sent);
3304 SET_ALLOW(harmony_restrictive_declarations); 3302 SET_ALLOW(harmony_restrictive_declarations);
3305 SET_ALLOW(harmony_async_await); 3303 SET_ALLOW(harmony_async_await);
3306 SET_ALLOW(harmony_trailing_commas); 3304 SET_ALLOW(harmony_trailing_commas);
3307 SET_ALLOW(harmony_class_fields); 3305 SET_ALLOW(harmony_class_fields);
3308 #undef SET_ALLOW 3306 #undef SET_ALLOW
3309 } 3307 }
3310 // Aborting inner function preparsing would leave scopes in an inconsistent 3308 // Aborting inner function preparsing would leave scopes in an inconsistent
3311 // state; we don't parse inner functions in the abortable mode anyway. 3309 // state; we don't parse inner functions in the abortable mode anyway.
3312 DCHECK(!is_inner_function || !may_abort); 3310 DCHECK(!is_inner_function || !may_abort);
3313 3311
3314 PreParser::PreParseResult result = reusable_preparser_->PreParseFunction( 3312 PreParser::PreParseResult result = reusable_preparser_->PreParseFunction(
3315 kind, function_scope, parsing_module_, logger, is_inner_function, 3313 kind, function_scope, parsing_module_, is_inner_function, may_abort,
3316 may_abort, use_counts_); 3314 use_counts_);
3317 return result; 3315 return result;
3318 } 3316 }
3319 3317
3320 Expression* Parser::InstallHomeObject(Expression* function_literal, 3318 Expression* Parser::InstallHomeObject(Expression* function_literal,
3321 Expression* home_object) { 3319 Expression* home_object) {
3322 Block* do_block = factory()->NewBlock(nullptr, 1, false, kNoSourcePosition); 3320 Block* do_block = factory()->NewBlock(nullptr, 1, false, kNoSourcePosition);
3323 Variable* result_var = 3321 Variable* result_var =
3324 scope()->NewTemporary(ast_value_factory()->empty_string()); 3322 scope()->NewTemporary(ast_value_factory()->empty_string());
3325 DoExpression* do_expr = 3323 DoExpression* do_expr =
3326 factory()->NewDoExpression(do_block, result_var, kNoSourcePosition); 3324 factory()->NewDoExpression(do_block, result_var, kNoSourcePosition);
(...skipping 478 matching lines...) Expand 10 before | Expand all | Expand 10 after
3805 return (result != NULL); 3803 return (result != NULL);
3806 } 3804 }
3807 3805
3808 3806
3809 void Parser::ParseOnBackground(ParseInfo* info) { 3807 void Parser::ParseOnBackground(ParseInfo* info) {
3810 parsing_on_main_thread_ = false; 3808 parsing_on_main_thread_ = false;
3811 3809
3812 DCHECK(info->literal() == NULL); 3810 DCHECK(info->literal() == NULL);
3813 FunctionLiteral* result = NULL; 3811 FunctionLiteral* result = NULL;
3814 3812
3815 CompleteParserRecorder recorder; 3813 ParserLogger logger;
3816 if (produce_cached_parse_data()) log_ = &recorder; 3814 if (produce_cached_parse_data()) log_ = &logger;
3817 3815
3818 std::unique_ptr<Utf16CharacterStream> stream; 3816 std::unique_ptr<Utf16CharacterStream> stream;
3819 Utf16CharacterStream* stream_ptr; 3817 Utf16CharacterStream* stream_ptr;
3820 if (info->character_stream()) { 3818 if (info->character_stream()) {
3821 DCHECK(info->source_stream() == nullptr); 3819 DCHECK(info->source_stream() == nullptr);
3822 stream_ptr = info->character_stream(); 3820 stream_ptr = info->character_stream();
3823 } else { 3821 } else {
3824 DCHECK(info->character_stream() == nullptr); 3822 DCHECK(info->character_stream() == nullptr);
3825 stream.reset(ScannerStream::For(info->source_stream(), 3823 stream.reset(ScannerStream::For(info->source_stream(),
3826 info->source_stream_encoding())); 3824 info->source_stream_encoding()));
(...skipping 16 matching lines...) Expand all
3843 } else { 3841 } else {
3844 result = DoParseFunction(info, info->function_name(), stream_ptr); 3842 result = DoParseFunction(info, info->function_name(), stream_ptr);
3845 } 3843 }
3846 3844
3847 info->set_literal(result); 3845 info->set_literal(result);
3848 3846
3849 // We cannot internalize on a background thread; a foreground task will take 3847 // We cannot internalize on a background thread; a foreground task will take
3850 // care of calling Parser::Internalize just before compilation. 3848 // care of calling Parser::Internalize just before compilation.
3851 3849
3852 if (produce_cached_parse_data()) { 3850 if (produce_cached_parse_data()) {
3853 if (result != NULL) *info->cached_data() = recorder.GetScriptData(); 3851 if (result != NULL) *info->cached_data() = logger.GetScriptData();
3854 log_ = NULL; 3852 log_ = NULL;
3855 } 3853 }
3856 } 3854 }
3857 3855
3858 Parser::TemplateLiteralState Parser::OpenTemplateLiteral(int pos) { 3856 Parser::TemplateLiteralState Parser::OpenTemplateLiteral(int pos) {
3859 return new (zone()) TemplateLiteral(zone(), pos); 3857 return new (zone()) TemplateLiteral(zone(), pos);
3860 } 3858 }
3861 3859
3862 3860
3863 void Parser::AddTemplateSpan(TemplateLiteralState* state, bool tail) { 3861 void Parser::AddTemplateSpan(TemplateLiteralState* state, bool tail) {
(...skipping 1559 matching lines...) Expand 10 before | Expand all | Expand 10 after
5423 5421
5424 return final_loop; 5422 return final_loop;
5425 } 5423 }
5426 5424
5427 #undef CHECK_OK 5425 #undef CHECK_OK
5428 #undef CHECK_OK_VOID 5426 #undef CHECK_OK_VOID
5429 #undef CHECK_FAILED 5427 #undef CHECK_FAILED
5430 5428
5431 } // namespace internal 5429 } // namespace internal
5432 } // namespace v8 5430 } // namespace v8
OLDNEW
« no previous file with comments | « src/parsing/parser.h ('k') | src/parsing/parser-base.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698