Commit d0b6686c authored by jwolfe's avatar jwolfe Committed by Commit bot

In parallel to the strict octal check that would reject `012` in strict mode,...

In parallel to the strict octal check that would reject `012` in strict mode, this patch collects UseCounters for `089` in strict mode. The spec says this should be an error, but this patch does not report it as such.

BUG=v8:4973
LOG=y

Review-Url: https://codereview.chromium.org/1948403002
Cr-Commit-Position: refs/heads/master@{#36221}
parent 02b7373a
......@@ -5625,9 +5625,10 @@ class V8_EXPORT Isolate {
kLegacyFunctionDeclaration = 29,
kRegExpPrototypeSourceGetter = 30,
kRegExpPrototypeOldFlagGetter = 31,
kDecimalWithLeadingZeroInStrictMode = 32,
// If you add new values here, you'll also need to update V8Initializer.cpp
// in Chromium.
// If you add new values here, you'll also need to update Chromium's:
// UseCounter.h, V8PerIsolateData.cpp, histograms.xml
kUseCounterFeatureCount // This enum value must be last.
};
......
......@@ -633,6 +633,18 @@ class ParserBase : public Traits {
*ok = false;
}
}
// for now, this check just collects statistics.
void CheckDecimalLiteralWithLeadingZero(int* use_counts, int beg_pos,
int end_pos) {
Scanner::Location token_location =
scanner()->decimal_with_leading_zero_position();
if (token_location.IsValid() && beg_pos <= token_location.beg_pos &&
token_location.end_pos <= end_pos) {
scanner()->clear_decimal_with_leading_zero_position();
if (use_counts != nullptr)
++use_counts[v8::Isolate::kDecimalWithLeadingZeroInStrictMode];
}
}
inline void CheckStrictOctalLiteral(int beg_pos, int end_pos, bool* ok) {
CheckOctalLiteral(beg_pos, end_pos, MessageTemplate::kStrictOctalLiteral,
......
......@@ -943,6 +943,8 @@ FunctionLiteral* Parser::DoParseProgram(ParseInfo* info) {
if (ok && is_strict(language_mode())) {
CheckStrictOctalLiteral(beg_pos, scanner()->location().end_pos, &ok);
CheckDecimalLiteralWithLeadingZero(use_counts_, beg_pos,
scanner()->location().end_pos);
}
if (ok && is_sloppy(language_mode())) {
// TODO(littledan): Function bindings on the global object that modify
......@@ -4175,6 +4177,8 @@ FunctionLiteral* Parser::ParseFunctionLiteral(
if (is_strict(language_mode)) {
CheckStrictOctalLiteral(scope->start_position(), scope->end_position(),
CHECK_OK);
CheckDecimalLiteralWithLeadingZero(use_counts_, scope->start_position(),
scope->end_position());
}
if (is_sloppy(language_mode)) {
InsertSloppyBlockFunctionVarBindings(scope, CHECK_OK);
......
......@@ -134,6 +134,7 @@ PreParser::PreParseResult PreParser::PreParseLazyFunction(
if (is_strict(scope_->language_mode())) {
int end_pos = scanner()->location().end_pos;
CheckStrictOctalLiteral(start_position, end_pos, &ok);
CheckDecimalLiteralWithLeadingZero(use_counts, start_position, end_pos);
if (!ok) return kPreParseSuccess;
}
}
......@@ -1106,6 +1107,8 @@ PreParser::Expression PreParser::ParseFunctionLiteral(
if (is_strict(language_mode)) {
int end_position = scanner()->location().end_pos;
CheckStrictOctalLiteral(start_position, end_position, CHECK_OK);
CheckDecimalLiteralWithLeadingZero(use_counts_, start_position,
end_position);
}
return Expression::Default();
......
......@@ -1031,6 +1031,8 @@ class PreParser : public ParserBase<PreParserTraits> {
} else if (is_strict(scope_->language_mode())) {
CheckStrictOctalLiteral(start_position, scanner()->location().end_pos,
&ok);
CheckDecimalLiteralWithLeadingZero(use_counts_, start_position,
scanner()->location().end_pos);
}
if (materialized_literals) {
*materialized_literals = function_state_->materialized_literal_count();
......
......@@ -40,6 +40,7 @@ Scanner::Scanner(UnicodeCache* unicode_cache)
: unicode_cache_(unicode_cache),
bookmark_c0_(kNoBookmark),
octal_pos_(Location::invalid()),
decimal_with_leading_zero_pos_(Location::invalid()),
found_html_comment_(false),
allow_harmony_exponentiation_operator_(false) {
bookmark_current_.literal_chars = &bookmark_current_literal_;
......@@ -975,10 +976,18 @@ void Scanner::ScanDecimalDigits() {
Token::Value Scanner::ScanNumber(bool seen_period) {
DCHECK(IsDecimalDigit(c0_)); // the first digit of the number or the fraction
enum { DECIMAL, HEX, OCTAL, IMPLICIT_OCTAL, BINARY } kind = DECIMAL;
enum {
DECIMAL,
DECIMAL_WITH_LEADING_ZERO,
HEX,
OCTAL,
IMPLICIT_OCTAL,
BINARY
} kind = DECIMAL;
LiteralScope literal(this);
bool at_start = !seen_period;
int start_pos; // For reporting octal positions.
if (seen_period) {
// we have already seen a decimal point of the float
AddLiteralChar('.');
......@@ -987,7 +996,7 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
} else {
// if the first character is '0' we must check for octals and hex
if (c0_ == '0') {
int start_pos = source_pos(); // For reporting octal positions.
start_pos = source_pos();
AddLiteralCharAdvance();
// either 0, 0exxx, 0Exxx, 0.xxx, a hex number, a binary number or
......@@ -1029,7 +1038,7 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
while (true) {
if (c0_ == '8' || c0_ == '9') {
at_start = false;
kind = DECIMAL;
kind = DECIMAL_WITH_LEADING_ZERO;
break;
}
if (c0_ < '0' || '7' < c0_) {
......@@ -1039,11 +1048,13 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
}
AddLiteralCharAdvance();
}
} else if (c0_ == '8' || c0_ == '9') {
kind = DECIMAL_WITH_LEADING_ZERO;
}
}
// Parse decimal digits and allow trailing fractional part.
if (kind == DECIMAL) {
if (kind == DECIMAL || kind == DECIMAL_WITH_LEADING_ZERO) {
if (at_start) {
uint64_t value = 0;
while (IsDecimalDigit(c0_)) {
......@@ -1060,6 +1071,8 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
literal.Complete();
HandleLeadSurrogate();
if (kind == DECIMAL_WITH_LEADING_ZERO)
decimal_with_leading_zero_pos_ = Location(start_pos, source_pos());
return Token::SMI;
}
HandleLeadSurrogate();
......@@ -1076,7 +1089,8 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
// scan exponent, if any
if (c0_ == 'e' || c0_ == 'E') {
DCHECK(kind != HEX); // 'e'/'E' must be scanned as part of the hex number
if (kind != DECIMAL) return Token::ILLEGAL;
if (!(kind == DECIMAL || kind == DECIMAL_WITH_LEADING_ZERO))
return Token::ILLEGAL;
// scan exponent
AddLiteralCharAdvance();
if (c0_ == '+' || c0_ == '-')
......@@ -1098,6 +1112,8 @@ Token::Value Scanner::ScanNumber(bool seen_period) {
literal.Complete();
if (kind == DECIMAL_WITH_LEADING_ZERO)
decimal_with_leading_zero_pos_ = Location(start_pos, source_pos());
return Token::NUMBER;
}
......
......@@ -425,6 +425,13 @@ class Scanner {
// Returns the location of the last seen octal literal.
Location octal_position() const { return octal_pos_; }
void clear_octal_position() { octal_pos_ = Location::invalid(); }
// Returns the location of the last seen decimal literal with a leading zero.
Location decimal_with_leading_zero_position() const {
return decimal_with_leading_zero_pos_;
}
void clear_decimal_with_leading_zero_position() {
decimal_with_leading_zero_pos_ = Location::invalid();
}
// Returns the value of the last smi that was scanned.
int smi_value() const { return current_.smi_value_; }
......@@ -772,9 +779,9 @@ class Scanner {
// Input stream. Must be initialized to an Utf16CharacterStream.
Utf16CharacterStream* source_;
// Start position of the octal literal last scanned.
// Last-seen positions of potentially problematic tokens.
Location octal_pos_;
Location decimal_with_leading_zero_pos_;
// One Unicode character look-ahead; c0_ < 0 at the end of the input.
uc32 c0_;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment