Revision: 19892
Author: [email protected]
Date: Thu Mar 13 11:56:13 2014 UTC
Log: Only call to LogSymbol when needed.
[email protected]
BUG=
Review URL: https://codereview.chromium.org/198903002
http://code.google.com/p/v8/source/detail?r=19892
Modified:
/branches/bleeding_edge/src/parser.cc
/branches/bleeding_edge/src/preparse-data.cc
/branches/bleeding_edge/src/preparse-data.h
/branches/bleeding_edge/src/preparser.cc
/branches/bleeding_edge/test/cctest/test-parsing.cc
=======================================
--- /branches/bleeding_edge/src/parser.cc Thu Mar 13 09:15:14 2014 UTC
+++ /branches/bleeding_edge/src/parser.cc Thu Mar 13 11:56:13 2014 UTC
@@ -3491,99 +3491,6 @@
}
-class SingletonLogger : public ParserRecorder {
- public:
- SingletonLogger() : has_error_(false), start_(-1), end_(-1) { }
- virtual ~SingletonLogger() { }
-
- void Reset() { has_error_ = false; }
-
- virtual void LogFunction(int start,
- int end,
- int literals,
- int properties,
- StrictMode strict_mode) {
- ASSERT(!has_error_);
- start_ = start;
- end_ = end;
- literals_ = literals;
- properties_ = properties;
- strict_mode_ = strict_mode;
- };
-
- // Logs a symbol creation of a literal or identifier.
- virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal)
{ }
- virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal)
{ }
-
- // Logs an error message and marks the log as containing an error.
- // Further logging will be ignored, and ExtractData will return a vector
- // representing the error only.
- virtual void LogMessage(int start,
- int end,
- const char* message,
- const char* argument_opt) {
- if (has_error_) return;
- has_error_ = true;
- start_ = start;
- end_ = end;
- message_ = message;
- argument_opt_ = argument_opt;
- }
-
- virtual int function_position() { return 0; }
-
- virtual int symbol_position() { return 0; }
-
- virtual int symbol_ids() { return -1; }
-
- virtual Vector<unsigned> ExtractData() {
- UNREACHABLE();
- return Vector<unsigned>();
- }
-
- virtual void PauseRecording() { }
-
- virtual void ResumeRecording() { }
-
- bool has_error() { return has_error_; }
-
- int start() { return start_; }
- int end() { return end_; }
- int literals() {
- ASSERT(!has_error_);
- return literals_;
- }
- int properties() {
- ASSERT(!has_error_);
- return properties_;
- }
- StrictMode strict_mode() {
- ASSERT(!has_error_);
- return strict_mode_;
- }
- const char* message() {
- ASSERT(has_error_);
- return message_;
- }
- const char* argument_opt() {
- ASSERT(has_error_);
- return argument_opt_;
- }
-
- private:
- bool has_error_;
- int start_;
- int end_;
- // For function entries.
- int literals_;
- int properties_;
- StrictMode strict_mode_;
- // For error messages.
- const char* message_;
- const char* argument_opt_;
-};
-
-
FunctionLiteral* Parser::ParseFunctionLiteral(
Handle<String> function_name,
Scanner::Location function_name_location,
=======================================
--- /branches/bleeding_edge/src/preparse-data.cc Tue Feb 25 11:51:02 2014
UTC
+++ /branches/bleeding_edge/src/preparse-data.cc Thu Mar 13 11:56:13 2014
UTC
@@ -37,13 +37,40 @@
namespace v8 {
namespace internal {
-//
----------------------------------------------------------------------------
-// FunctionLoggingParserRecorder
-FunctionLoggingParserRecorder::FunctionLoggingParserRecorder()
+template <typename Char>
+static int vector_hash(Vector<const Char> string) {
+ int hash = 0;
+ for (int i = 0; i < string.length(); i++) {
+ int c = static_cast<int>(string[i]);
+ hash += c;
+ hash += (hash << 10);
+ hash ^= (hash >> 6);
+ }
+ return hash;
+}
+
+
+static bool vector_compare(void* a, void* b) {
+ CompleteParserRecorder::Key* string1 =
+ reinterpret_cast<CompleteParserRecorder::Key*>(a);
+ CompleteParserRecorder::Key* string2 =
+ reinterpret_cast<CompleteParserRecorder::Key*>(b);
+ if (string1->is_one_byte != string2->is_one_byte) return false;
+ int length = string1->literal_bytes.length();
+ if (string2->literal_bytes.length() != length) return false;
+ return memcmp(string1->literal_bytes.start(),
+ string2->literal_bytes.start(), length) == 0;
+}
+
+
+CompleteParserRecorder::CompleteParserRecorder()
: function_store_(0),
- is_recording_(true),
- pause_count_(0) {
+ literal_chars_(0),
+ symbol_store_(0),
+ symbol_keys_(0),
+ string_table_(vector_compare),
+ symbol_id_(0) {
preamble_[PreparseDataConstants::kMagicOffset] =
PreparseDataConstants::kMagicNumber;
preamble_[PreparseDataConstants::kVersionOffset] =
@@ -56,10 +83,11 @@
#ifdef DEBUG
prev_start_ = -1;
#endif
+ should_log_symbols_ = true;
}
-void FunctionLoggingParserRecorder::LogMessage(int start_pos,
+void CompleteParserRecorder::LogMessage(int start_pos,
int end_pos,
const char* message,
const char* arg_opt) {
@@ -75,55 +103,39 @@
STATIC_ASSERT(PreparseDataConstants::kMessageTextPos == 3);
WriteString(CStrVector(message));
if (arg_opt != NULL) WriteString(CStrVector(arg_opt));
- is_recording_ = false;
+ should_log_symbols_ = false;
}
-void FunctionLoggingParserRecorder::WriteString(Vector<const char> str) {
+void CompleteParserRecorder::WriteString(Vector<const char> str) {
function_store_.Add(str.length());
for (int i = 0; i < str.length(); i++) {
function_store_.Add(str[i]);
}
}
-
-//
----------------------------------------------------------------------------
-// PartialParserRecorder - Record both function entries and symbols.
-Vector<unsigned> PartialParserRecorder::ExtractData() {
- int function_size = function_store_.size();
- int total_size = PreparseDataConstants::kHeaderSize + function_size;
- Vector<unsigned> data = Vector<unsigned>::New(total_size);
- preamble_[PreparseDataConstants::kFunctionsSizeOffset] = function_size;
- preamble_[PreparseDataConstants::kSymbolCountOffset] = 0;
- OS::MemCopy(data.start(), preamble_, sizeof(preamble_));
- int symbol_start = PreparseDataConstants::kHeaderSize + function_size;
- if (function_size > 0) {
-
function_store_.WriteTo(data.SubVector(PreparseDataConstants::kHeaderSize,
- symbol_start));
- }
- return data;
+void CompleteParserRecorder::LogOneByteSymbol(int start,
+ Vector<const uint8_t>
literal) {
+ ASSERT(should_log_symbols_);
+ int hash = vector_hash(literal);
+ LogSymbol(start, hash, true, literal);
}
-
-//
----------------------------------------------------------------------------
-// CompleteParserRecorder - Record both function entries and symbols.
-CompleteParserRecorder::CompleteParserRecorder()
- : FunctionLoggingParserRecorder(),
- literal_chars_(0),
- symbol_store_(0),
- symbol_keys_(0),
- string_table_(vector_compare),
- symbol_id_(0) {
+void CompleteParserRecorder::LogTwoByteSymbol(int start,
+ Vector<const uint16_t>
literal) {
+ ASSERT(should_log_symbols_);
+ int hash = vector_hash(literal);
+ LogSymbol(start, hash, false, Vector<const byte>::cast(literal));
}
void CompleteParserRecorder::LogSymbol(int start,
int hash,
- bool is_ascii,
+ bool is_one_byte,
Vector<const byte> literal_bytes) {
- Key key = { is_ascii, literal_bytes };
+ Key key = { is_one_byte, literal_bytes };
HashMap::Entry* entry = string_table_.Lookup(&key, hash, true);
int id = static_cast<int>(reinterpret_cast<intptr_t>(entry->value));
if (id == 0) {
=======================================
--- /branches/bleeding_edge/src/preparse-data.h Thu Mar 13 09:15:14 2014 UTC
+++ /branches/bleeding_edge/src/preparse-data.h Thu Mar 13 11:56:13 2014 UTC
@@ -35,13 +35,11 @@
namespace v8 {
namespace internal {
-//
----------------------------------------------------------------------------
-// ParserRecorder - Logging of preparser data.
// Abstract interface for preparse data recorder.
class ParserRecorder {
public:
- ParserRecorder() { }
+ ParserRecorder() : should_log_symbols_(false) { }
virtual ~ParserRecorder() { }
// Logs the scope and some details of a function literal in the source.
@@ -51,10 +49,6 @@
int properties,
StrictMode strict_mode) = 0;
- // Logs a symbol creation of a literal or identifier.
- virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal)
= 0;
- virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal)
= 0;
-
// Logs an error message and marks the log as containing an error.
// Further logging will be ignored, and ExtractData will return a vector
// representing the error only.
@@ -63,27 +57,110 @@
const char* message,
const char* argument_opt) = 0;
- virtual int function_position() = 0;
+ // Logs a symbol creation of a literal or identifier.
+ bool ShouldLogSymbols() { return should_log_symbols_; }
+ // The following functions are only callable on CompleteParserRecorder
+ // and are guarded by calls to ShouldLogSymbols.
+ virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal) {
+ UNREACHABLE();
+ }
+ virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal)
{
+ UNREACHABLE();
+ }
+ virtual void PauseRecording() { UNREACHABLE(); }
+ virtual void ResumeRecording() { UNREACHABLE(); }
- virtual int symbol_position() = 0;
+ protected:
+ bool should_log_symbols_;
- virtual int symbol_ids() = 0;
+ private:
+ DISALLOW_COPY_AND_ASSIGN(ParserRecorder);
+};
- virtual Vector<unsigned> ExtractData() = 0;
- virtual void PauseRecording() = 0;
+class SingletonLogger : public ParserRecorder {
+ public:
+ SingletonLogger() : has_error_(false), start_(-1), end_(-1) { }
+ virtual ~SingletonLogger() { }
- virtual void ResumeRecording() = 0;
+ void Reset() { has_error_ = false; }
+
+ virtual void LogFunction(int start,
+ int end,
+ int literals,
+ int properties,
+ StrictMode strict_mode) {
+ ASSERT(!has_error_);
+ start_ = start;
+ end_ = end;
+ literals_ = literals;
+ properties_ = properties;
+ strict_mode_ = strict_mode;
+ };
+
+ // Logs an error message and marks the log as containing an error.
+ // Further logging will be ignored, and ExtractData will return a vector
+ // representing the error only.
+ virtual void LogMessage(int start,
+ int end,
+ const char* message,
+ const char* argument_opt) {
+ if (has_error_) return;
+ has_error_ = true;
+ start_ = start;
+ end_ = end;
+ message_ = message;
+ argument_opt_ = argument_opt;
+ }
+
+ bool has_error() { return has_error_; }
+
+ int start() { return start_; }
+ int end() { return end_; }
+ int literals() {
+ ASSERT(!has_error_);
+ return literals_;
+ }
+ int properties() {
+ ASSERT(!has_error_);
+ return properties_;
+ }
+ StrictMode strict_mode() {
+ ASSERT(!has_error_);
+ return strict_mode_;
+ }
+ const char* message() {
+ ASSERT(has_error_);
+ return message_;
+ }
+ const char* argument_opt() {
+ ASSERT(has_error_);
+ return argument_opt_;
+ }
+
+ private:
+ bool has_error_;
+ int start_;
+ int end_;
+ // For function entries.
+ int literals_;
+ int properties_;
+ StrictMode strict_mode_;
+ // For error messages.
+ const char* message_;
+ const char* argument_opt_;
};
-//
----------------------------------------------------------------------------
-// FunctionLoggingParserRecorder - Record only function entries
-
-class FunctionLoggingParserRecorder : public ParserRecorder {
+class CompleteParserRecorder : public ParserRecorder {
public:
- FunctionLoggingParserRecorder();
- virtual ~FunctionLoggingParserRecorder() {}
+ struct Key {
+ bool is_one_byte;
+ Vector<const byte> literal_bytes;
+ };
+
+ CompleteParserRecorder();
+ virtual ~CompleteParserRecorder() {}
virtual void LogFunction(int start,
int end,
@@ -105,122 +182,44 @@
const char* message,
const char* argument_opt);
- virtual int function_position() { return function_store_.size(); }
-
-
- virtual Vector<unsigned> ExtractData() = 0;
-
virtual void PauseRecording() {
- pause_count_++;
- is_recording_ = false;
+ ASSERT(should_log_symbols_);
+ should_log_symbols_ = false;
}
virtual void ResumeRecording() {
- ASSERT(pause_count_ > 0);
- if (--pause_count_ == 0) is_recording_ = !has_error();
+ ASSERT(!should_log_symbols_);
+ should_log_symbols_ = !has_error();
}
- protected:
+ virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal);
+ virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal);
+ Vector<unsigned> ExtractData();
+
+ private:
bool has_error() {
return
static_cast<bool>(preamble_[PreparseDataConstants::kHasErrorOffset]);
}
-
- bool is_recording() {
- return is_recording_;
- }
void WriteString(Vector<const char> str);
+ // For testing. Defined in test-parsing.cc.
+ friend struct CompleteParserRecorderFriend;
+
+ void LogSymbol(int start,
+ int hash,
+ bool is_one_byte,
+ Vector<const byte> literal);
+
+ // Write a non-negative number to the symbol store.
+ void WriteNumber(int number);
+
Collector<unsigned> function_store_;
unsigned preamble_[PreparseDataConstants::kHeaderSize];
- bool is_recording_;
- int pause_count_;
#ifdef DEBUG
int prev_start_;
#endif
-};
-
-
-//
----------------------------------------------------------------------------
-// PartialParserRecorder - Record only function entries
-
-class PartialParserRecorder : public FunctionLoggingParserRecorder {
- public:
- PartialParserRecorder() : FunctionLoggingParserRecorder() { }
- virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal)
{ }
- virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal)
{ }
- virtual ~PartialParserRecorder() { }
- virtual Vector<unsigned> ExtractData();
- virtual int symbol_position() { return 0; }
- virtual int symbol_ids() { return 0; }
-};
-
-
-//
----------------------------------------------------------------------------
-// CompleteParserRecorder - Record both function entries and symbols.
-
-class CompleteParserRecorder: public FunctionLoggingParserRecorder {
- public:
- CompleteParserRecorder();
- virtual ~CompleteParserRecorder() { }
-
- virtual void LogOneByteSymbol(int start, Vector<const uint8_t> literal) {
- if (!is_recording_) return;
- int hash = vector_hash(literal);
- LogSymbol(start, hash, true, literal);
- }
-
- virtual void LogTwoByteSymbol(int start, Vector<const uint16_t> literal)
{
- if (!is_recording_) return;
- int hash = vector_hash(literal);
- LogSymbol(start, hash, false, Vector<const byte>::cast(literal));
- }
-
- virtual Vector<unsigned> ExtractData();
-
- virtual int symbol_position() { return symbol_store_.size(); }
- virtual int symbol_ids() { return symbol_id_; }
-
- private:
- // For testing. Defined in test-parsing.cc.
- friend void FakeWritingSymbolIdInPreParseData(CompleteParserRecorder*
log,
- int number);
-
- struct Key {
- bool is_ascii;
- Vector<const byte> literal_bytes;
- };
-
- virtual void LogSymbol(int start,
- int hash,
- bool is_ascii,
- Vector<const byte> literal);
-
- template <typename Char>
- static int vector_hash(Vector<const Char> string) {
- int hash = 0;
- for (int i = 0; i < string.length(); i++) {
- int c = static_cast<int>(string[i]);
- hash += c;
- hash += (hash << 10);
- hash ^= (hash >> 6);
- }
- return hash;
- }
-
- static bool vector_compare(void* a, void* b) {
- Key* string1 = reinterpret_cast<Key*>(a);
- Key* string2 = reinterpret_cast<Key*>(b);
- if (string1->is_ascii != string2->is_ascii) return false;
- int length = string1->literal_bytes.length();
- if (string2->literal_bytes.length() != length) return false;
- return memcmp(string1->literal_bytes.start(),
- string2->literal_bytes.start(), length) == 0;
- }
-
- // Write a non-negative number to the symbol store.
- void WriteNumber(int number);
Collector<byte> literal_chars_;
Collector<byte> symbol_store_;
=======================================
--- /branches/bleeding_edge/src/preparser.cc Thu Mar 13 08:29:31 2014 UTC
+++ /branches/bleeding_edge/src/preparser.cc Thu Mar 13 11:56:13 2014 UTC
@@ -1232,9 +1232,10 @@
void PreParser::ParseLazyFunctionLiteralBody(bool* ok) {
int body_start = position();
- log_->PauseRecording();
+ bool is_logging = log_->ShouldLogSymbols();
+ if (is_logging) log_->PauseRecording();
ParseSourceElements(Token::RBRACE, ok);
- log_->ResumeRecording();
+ if (is_logging) log_->ResumeRecording();
if (!*ok) return;
// Position right after terminal '}'.
@@ -1266,7 +1267,9 @@
void PreParser::LogSymbol() {
- scanner()->LogSymbol(log_, position());
+ if (log_->ShouldLogSymbols()) {
+ scanner()->LogSymbol(log_, position());
+ }
}
=======================================
--- /branches/bleeding_edge/test/cctest/test-parsing.cc Thu Mar 13 09:14:16
2014 UTC
+++ /branches/bleeding_edge/test/cctest/test-parsing.cc Thu Mar 13 11:56:13
2014 UTC
@@ -364,13 +364,24 @@
namespace v8 {
namespace internal {
-void FakeWritingSymbolIdInPreParseData(i::CompleteParserRecorder* log,
- int number) {
- log->WriteNumber(number);
- if (log->symbol_id_ < number + 1) {
- log->symbol_id_ = number + 1;
+struct CompleteParserRecorderFriend {
+ static void FakeWritingSymbolIdInPreParseData(CompleteParserRecorder*
log,
+ int number) {
+ log->WriteNumber(number);
+ if (log->symbol_id_ < number + 1) {
+ log->symbol_id_ = number + 1;
+ }
}
-}
+ static int symbol_position(CompleteParserRecorder* log) {
+ return log->symbol_store_.size();
+ }
+ static int symbol_ids(CompleteParserRecorder* log) {
+ return log->symbol_id_;
+ }
+ static int function_position(CompleteParserRecorder* log) {
+ return log->function_store_.size();
+ }
+};
}
}
@@ -380,15 +391,16 @@
// Symbol IDs are split into chunks of 7 bits for storing. This is a
// regression test for a bug where a symbol id was incorrectly stored if
some
// of the chunks in the middle were all zeros.
+ typedef i::CompleteParserRecorderFriend F;
i::CompleteParserRecorder log;
for (int i = 0; i < 18; ++i) {
- FakeWritingSymbolIdInPreParseData(&log, 1 << i);
+ F::FakeWritingSymbolIdInPreParseData(&log, 1 << i);
}
for (int i = 1; i < 18; ++i) {
- FakeWritingSymbolIdInPreParseData(&log, (1 << i) + 1);
+ F::FakeWritingSymbolIdInPreParseData(&log, (1 << i) + 1);
}
for (int i = 6; i < 18; ++i) {
- FakeWritingSymbolIdInPreParseData(&log, (3 << i) + (5 << (i - 6)));
+ F::FakeWritingSymbolIdInPreParseData(&log, (3 << i) + (5 << (i - 6)));
}
i::Vector<unsigned> store = log.ExtractData();
i::ScriptDataImpl script_data(store);
@@ -2008,6 +2020,7 @@
// Each function adds 5 elements to the preparse function data.
const int kDataPerFunction = 5;
+ typedef i::CompleteParserRecorderFriend F;
uintptr_t stack_limit =
CcTest::i_isolate()->stack_guard()->real_climit();
for (int i = 0; test_cases[i].program; i++) {
const char* program = test_cases[i].program;
@@ -2023,21 +2036,22 @@
preparser.set_allow_natives_syntax(true);
i::PreParser::PreParseResult result = preparser.PreParseProgram();
CHECK_EQ(i::PreParser::kPreParseSuccess, result);
- if (log.symbol_ids() != test_cases[i].symbols) {
+ if (F::symbol_ids(&log) != test_cases[i].symbols) {
i::OS::Print(
"Expected preparse data for program:\n"
"\t%s\n"
"to contain %d symbols, however, received %d symbols.\n",
- program, test_cases[i].symbols, log.symbol_ids());
+ program, test_cases[i].symbols, F::symbol_ids(&log));
CHECK(false);
}
- if (log.function_position() != test_cases[i].functions *
kDataPerFunction) {
+ if (F::function_position(&log) !=
+ test_cases[i].functions * kDataPerFunction) {
i::OS::Print(
"Expected preparse data for program:\n"
"\t%s\n"
"to contain %d functions, however, received %d functions.\n",
program, test_cases[i].functions,
- log.function_position() / kDataPerFunction);
+ F::function_position(&log) / kDataPerFunction);
CHECK(false);
}
i::ScriptDataImpl data(log.ExtractData());
--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
---
You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.