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

Side by Side Diff: src/parser.cc

Issue 5723002: Make RegExp character class match JSC. (Closed)
Patch Set: Address review comments. Add tests Created 10 years 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 | « no previous file | test/mjsunit/regexp.js » ('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 2010 the V8 project authors. All rights reserved. 1 // Copyright 2010 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 4431 matching lines...) Expand 10 before | Expand all | Expand 10 after
4442 uc32 c = ParseClassCharacterEscape(CHECK_FAILED); 4442 uc32 c = ParseClassCharacterEscape(CHECK_FAILED);
4443 return CharacterRange::Singleton(c); 4443 return CharacterRange::Singleton(c);
4444 } 4444 }
4445 } else { 4445 } else {
4446 Advance(); 4446 Advance();
4447 return CharacterRange::Singleton(first); 4447 return CharacterRange::Singleton(first);
4448 } 4448 }
4449 } 4449 }
4450 4450
4451 4451
4452 static const uc16 kNoCharClass = 0;
4453
4454 // Adds range or pre-defined character class to character ranges.
4455 // If char_class is not kInvalidClass, it's interpreted as a class
4456 // escape (i.e., 's' means whitespace, from '\s').
4457 static inline void AddRangeOrEscape(ZoneList<CharacterRange>* ranges,
4458 uc16 char_class,
4459 CharacterRange range) {
4460 if (char_class != kNoCharClass) {
4461 CharacterRange::AddClassEscape(char_class, ranges);
4462 } else {
4463 ranges->Add(range);
4464 }
4465 }
4466
4467
4452 RegExpTree* RegExpParser::ParseCharacterClass() { 4468 RegExpTree* RegExpParser::ParseCharacterClass() {
4453 static const char* kUnterminated = "Unterminated character class"; 4469 static const char* kUnterminated = "Unterminated character class";
4454 static const char* kRangeOutOfOrder = "Range out of order in character class"; 4470 static const char* kRangeOutOfOrder = "Range out of order in character class";
4455 4471
4456 ASSERT_EQ(current(), '['); 4472 ASSERT_EQ(current(), '[');
4457 Advance(); 4473 Advance();
4458 bool is_negated = false; 4474 bool is_negated = false;
4459 if (current() == '^') { 4475 if (current() == '^') {
4460 is_negated = true; 4476 is_negated = true;
4461 Advance(); 4477 Advance();
4462 } 4478 }
4463 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2); 4479 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2);
4464 while (has_more() && current() != ']') { 4480 while (has_more() && current() != ']') {
4465 uc16 char_class = 0; 4481 uc16 char_class = kNoCharClass;
4466 CharacterRange first = ParseClassAtom(&char_class CHECK_FAILED); 4482 CharacterRange first = ParseClassAtom(&char_class CHECK_FAILED);
4467 if (char_class) {
4468 CharacterRange::AddClassEscape(char_class, ranges);
4469 continue;
4470 }
4471 if (current() == '-') { 4483 if (current() == '-') {
4472 Advance(); 4484 Advance();
4473 if (current() == kEndMarker) { 4485 if (current() == kEndMarker) {
4474 // If we reach the end we break out of the loop and let the 4486 // If we reach the end we break out of the loop and let the
4475 // following code report an error. 4487 // following code report an error.
4476 break; 4488 break;
4477 } else if (current() == ']') { 4489 } else if (current() == ']') {
4478 ranges->Add(first); 4490 AddRangeOrEscape(ranges, char_class, first);
4479 ranges->Add(CharacterRange::Singleton('-')); 4491 ranges->Add(CharacterRange::Singleton('-'));
4480 break; 4492 break;
4481 } 4493 }
4482 CharacterRange next = ParseClassAtom(&char_class CHECK_FAILED); 4494 uc16 char_class_2 = kNoCharClass;
4483 if (char_class) { 4495 CharacterRange next = ParseClassAtom(&char_class_2 CHECK_FAILED);
4484 ranges->Add(first); 4496 if (char_class != kNoCharClass || char_class_2 != kNoCharClass) {
4497 // Either end is an escaped character class. Treat the '-' verbatim.
4498 AddRangeOrEscape(ranges, char_class, first);
4485 ranges->Add(CharacterRange::Singleton('-')); 4499 ranges->Add(CharacterRange::Singleton('-'));
4486 CharacterRange::AddClassEscape(char_class, ranges); 4500 AddRangeOrEscape(ranges, char_class_2, next);
4487 continue; 4501 continue;
4488 } 4502 }
4489 if (first.from() > next.to()) { 4503 if (first.from() > next.to()) {
4490 return ReportError(CStrVector(kRangeOutOfOrder) CHECK_FAILED); 4504 return ReportError(CStrVector(kRangeOutOfOrder) CHECK_FAILED);
4491 } 4505 }
4492 ranges->Add(CharacterRange::Range(first.from(), next.to())); 4506 ranges->Add(CharacterRange::Range(first.from(), next.to()));
4493 } else { 4507 } else {
4494 ranges->Add(first); 4508 AddRangeOrEscape(ranges, char_class, first);
4495 } 4509 }
4496 } 4510 }
4497 if (!has_more()) { 4511 if (!has_more()) {
4498 return ReportError(CStrVector(kUnterminated) CHECK_FAILED); 4512 return ReportError(CStrVector(kUnterminated) CHECK_FAILED);
4499 } 4513 }
4500 Advance(); 4514 Advance();
4501 if (ranges->length() == 0) { 4515 if (ranges->length() == 0) {
4502 ranges->Add(CharacterRange::Everything()); 4516 ranges->Add(CharacterRange::Everything());
4503 is_negated = !is_negated; 4517 is_negated = !is_negated;
4504 } 4518 }
(...skipping 174 matching lines...) Expand 10 before | Expand all | Expand 10 after
4679 Handle<String> source = Handle<String>(String::cast(script->source())); 4693 Handle<String> source = Handle<String>(String::cast(script->source()));
4680 result = parser.ParseProgram(source, info->is_global()); 4694 result = parser.ParseProgram(source, info->is_global());
4681 } 4695 }
4682 } 4696 }
4683 4697
4684 info->SetFunction(result); 4698 info->SetFunction(result);
4685 return (result != NULL); 4699 return (result != NULL);
4686 } 4700 }
4687 4701
4688 } } // namespace v8::internal 4702 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « no previous file | test/mjsunit/regexp.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698