| OLD | NEW |
| 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 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 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 56 Handle<Object> index); | 56 Handle<Object> index); |
| 57 | 57 |
| 58 // Call RegExp.prototyp.exec(string) in a loop. | 58 // Call RegExp.prototyp.exec(string) in a loop. |
| 59 // Used by String.prototype.match and String.prototype.replace. | 59 // Used by String.prototype.match and String.prototype.replace. |
| 60 // This function calls the garbage collector if necessary. | 60 // This function calls the garbage collector if necessary. |
| 61 static Handle<Object> ExecGlobal(Handle<JSRegExp> regexp, | 61 static Handle<Object> ExecGlobal(Handle<JSRegExp> regexp, |
| 62 Handle<String> subject); | 62 Handle<String> subject); |
| 63 | 63 |
| 64 // Stores an uncompiled RegExp pattern in the JSRegExp object. | 64 // Stores an uncompiled RegExp pattern in the JSRegExp object. |
| 65 // It will be compiled by JSCRE when first executed. | 65 // It will be compiled by JSCRE when first executed. |
| 66 static Handle<Object> JsrePrepare(Handle<JSRegExp> re, | 66 static Handle<Object> JscrePrepare(Handle<JSRegExp> re, |
| 67 Handle<String> pattern, |
| 68 JSRegExp::Flags flags); |
| 69 |
| 70 // Stores a compiled RegExp pattern in the JSRegExp object. |
| 71 // The pattern is compiled by Regexp2000. |
| 72 static Handle<Object> Re2kPrepare(Handle<JSRegExp> re, |
| 67 Handle<String> pattern, | 73 Handle<String> pattern, |
| 68 JSRegExp::Flags flags); | 74 JSRegExp::Flags flags, |
| 75 Handle<FixedArray> re2k_data); |
| 76 |
| 69 | 77 |
| 70 // Compile the pattern using JSCRE and store the result in the | 78 // Compile the pattern using JSCRE and store the result in the |
| 71 // JSRegExp object. | 79 // JSRegExp object. |
| 72 static Handle<Object> JsreCompile(Handle<JSRegExp> re); | 80 static Handle<Object> JscreCompile(Handle<JSRegExp> re); |
| 73 | 81 |
| 74 static Handle<Object> AtomCompile(Handle<JSRegExp> re, | 82 static Handle<Object> AtomCompile(Handle<JSRegExp> re, |
| 75 Handle<String> pattern, | 83 Handle<String> pattern, |
| 76 JSRegExp::Flags flags, | 84 JSRegExp::Flags flags, |
| 77 Handle<String> match_pattern); | 85 Handle<String> match_pattern); |
| 78 static Handle<Object> AtomExec(Handle<JSRegExp> regexp, | 86 static Handle<Object> AtomExec(Handle<JSRegExp> regexp, |
| 79 Handle<String> subject, | 87 Handle<String> subject, |
| 80 Handle<Object> index); | 88 Handle<Object> index); |
| 81 | 89 |
| 82 static Handle<Object> AtomExecGlobal(Handle<JSRegExp> regexp, | 90 static Handle<Object> AtomExecGlobal(Handle<JSRegExp> regexp, |
| 83 Handle<String> subject); | 91 Handle<String> subject); |
| 84 | 92 |
| 85 static Handle<Object> JsreCompile(Handle<JSRegExp> re, | 93 static Handle<Object> JscreCompile(Handle<JSRegExp> re, |
| 86 Handle<String> pattern, | 94 Handle<String> pattern, |
| 87 JSRegExp::Flags flags); | 95 JSRegExp::Flags flags); |
| 88 | 96 |
| 89 // Execute a compiled JSCRE pattern. | 97 // Execute a compiled JSCRE pattern. |
| 90 static Handle<Object> JsreExec(Handle<JSRegExp> regexp, | 98 static Handle<Object> JscreExec(Handle<JSRegExp> regexp, |
| 99 Handle<String> subject, |
| 100 Handle<Object> index); |
| 101 |
| 102 // Execute a Regexp2000 bytecode pattern. |
| 103 static Handle<Object> Re2kExec(Handle<JSRegExp> regexp, |
| 91 Handle<String> subject, | 104 Handle<String> subject, |
| 92 Handle<Object> index); | 105 Handle<Object> index); |
| 93 | 106 |
| 94 static Handle<Object> JsreExecGlobal(Handle<JSRegExp> regexp, | 107 static Handle<Object> JscreExecGlobal(Handle<JSRegExp> regexp, |
| 108 Handle<String> subject); |
| 109 |
| 110 static Handle<Object> Re2kExecGlobal(Handle<JSRegExp> regexp, |
| 95 Handle<String> subject); | 111 Handle<String> subject); |
| 96 | 112 |
| 97 static void NewSpaceCollectionPrologue(); | 113 static void NewSpaceCollectionPrologue(); |
| 98 static void OldSpaceCollectionPrologue(); | 114 static void OldSpaceCollectionPrologue(); |
| 99 | 115 |
| 100 // Converts a source string to a 16 bit flat string. The string | 116 // Converts a source string to a 16 bit flat string. The string |
| 101 // will be either sequential or it will be a SlicedString backed | 117 // will be either sequential or it will be a SlicedString backed |
| 102 // by a flat string. | 118 // by a flat string. |
| 103 static Handle<String> StringToTwoByte(Handle<String> pattern); | 119 static Handle<String> StringToTwoByte(Handle<String> pattern); |
| 104 static Handle<String> CachedStringToTwoByte(Handle<String> pattern); | 120 static Handle<String> CachedStringToTwoByte(Handle<String> pattern); |
| 105 | 121 |
| 122 static const int kRe2kImplementationIndex = 0; |
| 123 static const int kRe2kNumberOfCapturesIndex = 1; |
| 124 static const int kRe2kNumberOfRegistersIndex = 2; |
| 125 static const int kRe2kCodeIndex = 3; |
| 126 static const int kRe2kDataLength = 4; |
| 127 |
| 128 static const int kJscreNumberOfCapturesIndex = 0; |
| 129 static const int kJscreInternalIndex = 1; |
| 130 static const int kJscreDataLength = 2; |
| 131 |
| 106 private: | 132 private: |
| 107 static String* last_ascii_string_; | 133 static String* last_ascii_string_; |
| 108 static String* two_byte_cached_string_; | 134 static String* two_byte_cached_string_; |
| 109 | 135 |
| 110 // Returns the caputure from the re. | 136 static int JscreNumberOfCaptures(Handle<JSRegExp> re); |
| 111 static int JsreCapture(Handle<JSRegExp> re); | 137 static ByteArray* JscreInternal(Handle<JSRegExp> re); |
| 112 static ByteArray* JsreInternal(Handle<JSRegExp> re); | 138 |
| 139 static int Re2kNumberOfCaptures(Handle<JSRegExp> re); |
| 140 static int Re2kNumberOfRegisters(Handle<JSRegExp> re); |
| 141 static Handle<ByteArray> Re2kCode(Handle<JSRegExp> re); |
| 113 | 142 |
| 114 // Call jsRegExpExecute once | 143 // Call jsRegExpExecute once |
| 115 static Handle<Object> JsreExecOnce(Handle<JSRegExp> regexp, | 144 static Handle<Object> JscreExecOnce(Handle<JSRegExp> regexp, |
| 145 int num_captures, |
| 146 Handle<String> subject, |
| 147 int previous_index, |
| 148 const uc16* utf8_subject, |
| 149 int* ovector, |
| 150 int ovector_length); |
| 151 |
| 152 static Handle<Object> Re2kExecOnce(Handle<JSRegExp> regexp, |
| 116 int num_captures, | 153 int num_captures, |
| 117 Handle<String> subject, | 154 Handle<String> subject, |
| 118 int previous_index, | 155 int previous_index, |
| 119 const uc16* utf8_subject, | 156 const uc16* utf8_subject, |
| 120 int* ovector, | 157 int* ovector, |
| 121 int ovector_length); | 158 int ovector_length); |
| 122 | 159 |
| 123 // Set the subject cache. The previous string buffer is not deleted, so the | 160 // Set the subject cache. The previous string buffer is not deleted, so the |
| 124 // caller should ensure that it doesn't leak. | 161 // caller should ensure that it doesn't leak. |
| 125 static void SetSubjectCache(String* subject, char* utf8_subject, | 162 static void SetSubjectCache(String* subject, |
| 126 int uft8_length, int character_position, | 163 char* utf8_subject, |
| 164 int uft8_length, |
| 165 int character_position, |
| 127 int utf8_position); | 166 int utf8_position); |
| 128 | 167 |
| 129 // A one element cache of the last utf8_subject string and its length. The | 168 // A one element cache of the last utf8_subject string and its length. The |
| 130 // subject JS String object is cached in the heap. We also cache a | 169 // subject JS String object is cached in the heap. We also cache a |
| 131 // translation between position and utf8 position. | 170 // translation between position and utf8 position. |
| 132 static char* utf8_subject_cache_; | 171 static char* utf8_subject_cache_; |
| 133 static int utf8_length_cache_; | 172 static int utf8_length_cache_; |
| 134 static int utf8_position_; | 173 static int utf8_position_; |
| 135 static int character_position_; | 174 static int character_position_; |
| 136 }; | 175 }; |
| (...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 355 VISIT(Choice) \ | 394 VISIT(Choice) \ |
| 356 VISIT(Backreference) \ | 395 VISIT(Backreference) \ |
| 357 VISIT(CharacterClass) | 396 VISIT(CharacterClass) |
| 358 | 397 |
| 359 | 398 |
| 360 class RegExpNode: public ZoneObject { | 399 class RegExpNode: public ZoneObject { |
| 361 public: | 400 public: |
| 362 virtual ~RegExpNode() { } | 401 virtual ~RegExpNode() { } |
| 363 virtual void Accept(NodeVisitor* visitor) = 0; | 402 virtual void Accept(NodeVisitor* visitor) = 0; |
| 364 // Generates a goto to this node or actually generates the code at this point. | 403 // Generates a goto to this node or actually generates the code at this point. |
| 365 void GoTo(RegExpCompiler* compiler); | 404 // Until the implementation is complete we will return true for success and |
| 405 // false for failure. |
| 406 bool GoTo(RegExpCompiler* compiler); |
| 366 void EmitAddress(RegExpCompiler* compiler); | 407 void EmitAddress(RegExpCompiler* compiler); |
| 367 virtual void Emit(RegExpCompiler* compiler) = 0; | 408 // Until the implementation is complete we will return true for success and |
| 409 // false for failure. |
| 410 virtual bool Emit(RegExpCompiler* compiler) = 0; |
| 368 private: | 411 private: |
| 369 Label label; | 412 Label label; |
| 370 }; | 413 }; |
| 371 | 414 |
| 372 | 415 |
| 373 class SeqRegExpNode: public RegExpNode { | 416 class SeqRegExpNode: public RegExpNode { |
| 374 public: | 417 public: |
| 375 explicit SeqRegExpNode(RegExpNode* on_success) | 418 explicit SeqRegExpNode(RegExpNode* on_success) |
| 376 : on_success_(on_success) { } | 419 : on_success_(on_success) { } |
| 377 RegExpNode* on_success() { return on_success_; } | 420 RegExpNode* on_success() { return on_success_; } |
| 378 virtual void Emit(RegExpCompiler* compiler) { UNREACHABLE(); } | 421 virtual bool Emit(RegExpCompiler* compiler) { return false; } |
| 379 private: | 422 private: |
| 380 RegExpNode* on_success_; | 423 RegExpNode* on_success_; |
| 381 }; | 424 }; |
| 382 | 425 |
| 383 | 426 |
| 384 class ActionNode: public SeqRegExpNode { | 427 class ActionNode: public SeqRegExpNode { |
| 385 public: | 428 public: |
| 386 enum Type { | 429 enum Type { |
| 387 STORE_REGISTER, | 430 STORE_REGISTER, |
| 388 INCREMENT_REGISTER, | 431 INCREMENT_REGISTER, |
| 389 STORE_POSITION, | 432 STORE_POSITION, |
| 390 RESTORE_POSITION, | 433 RESTORE_POSITION, |
| 391 BEGIN_SUBMATCH, | 434 BEGIN_SUBMATCH, |
| 392 ESCAPE_SUBMATCH, | 435 ESCAPE_SUBMATCH, |
| 393 END_SUBMATCH | 436 END_SUBMATCH |
| 394 }; | 437 }; |
| 395 static ActionNode* StoreRegister(int reg, int val, RegExpNode* on_success); | 438 static ActionNode* StoreRegister(int reg, int val, RegExpNode* on_success); |
| 396 static ActionNode* IncrementRegister(int reg, RegExpNode* on_success); | 439 static ActionNode* IncrementRegister(int reg, RegExpNode* on_success); |
| 397 static ActionNode* StorePosition(int reg, RegExpNode* on_success); | 440 static ActionNode* StorePosition(int reg, RegExpNode* on_success); |
| 398 static ActionNode* RestorePosition(int reg, RegExpNode* on_success); | 441 static ActionNode* RestorePosition(int reg, RegExpNode* on_success); |
| 399 static ActionNode* BeginSubmatch(RegExpNode* on_success); | 442 static ActionNode* BeginSubmatch(RegExpNode* on_success); |
| 400 static ActionNode* EscapeSubmatch(RegExpNode* on_success); | 443 static ActionNode* EscapeSubmatch(RegExpNode* on_success); |
| 401 static ActionNode* EndSubmatch(RegExpNode* on_success); | 444 static ActionNode* EndSubmatch(RegExpNode* on_success); |
| 402 virtual void Accept(NodeVisitor* visitor); | 445 virtual void Accept(NodeVisitor* visitor); |
| 403 virtual void Emit(RegExpCompiler* compiler); | 446 virtual bool Emit(RegExpCompiler* compiler); |
| 404 private: | 447 private: |
| 405 union { | 448 union { |
| 406 struct { | 449 struct { |
| 407 int reg; | 450 int reg; |
| 408 int value; | 451 int value; |
| 409 } u_store_register; | 452 } u_store_register; |
| 410 struct { | 453 struct { |
| 411 int reg; | 454 int reg; |
| 412 } u_increment_register; | 455 } u_increment_register; |
| 413 struct { | 456 struct { |
| (...skipping 12 matching lines...) Expand all Loading... |
| 426 public: | 469 public: |
| 427 AtomNode(Vector<const uc16> data, | 470 AtomNode(Vector<const uc16> data, |
| 428 RegExpNode* on_success, | 471 RegExpNode* on_success, |
| 429 RegExpNode* on_failure) | 472 RegExpNode* on_failure) |
| 430 : SeqRegExpNode(on_success), | 473 : SeqRegExpNode(on_success), |
| 431 on_failure_(on_failure), | 474 on_failure_(on_failure), |
| 432 data_(data) { } | 475 data_(data) { } |
| 433 virtual void Accept(NodeVisitor* visitor); | 476 virtual void Accept(NodeVisitor* visitor); |
| 434 Vector<const uc16> data() { return data_; } | 477 Vector<const uc16> data() { return data_; } |
| 435 RegExpNode* on_failure() { return on_failure_; } | 478 RegExpNode* on_failure() { return on_failure_; } |
| 436 virtual void Emit(RegExpCompiler* compiler) { UNREACHABLE(); } | 479 virtual bool Emit(RegExpCompiler* compiler) { return false; } |
| 437 private: | 480 private: |
| 438 RegExpNode* on_failure_; | 481 RegExpNode* on_failure_; |
| 439 Vector<const uc16> data_; | 482 Vector<const uc16> data_; |
| 440 }; | 483 }; |
| 441 | 484 |
| 442 | 485 |
| 443 class BackreferenceNode: public SeqRegExpNode { | 486 class BackreferenceNode: public SeqRegExpNode { |
| 444 public: | 487 public: |
| 445 BackreferenceNode(int start_reg, | 488 BackreferenceNode(int start_reg, |
| 446 int end_reg, | 489 int end_reg, |
| 447 RegExpNode* on_success, | 490 RegExpNode* on_success, |
| 448 RegExpNode* on_failure) | 491 RegExpNode* on_failure) |
| 449 : SeqRegExpNode(on_success), | 492 : SeqRegExpNode(on_success), |
| 450 on_failure_(on_failure), | 493 on_failure_(on_failure), |
| 451 start_reg_(start_reg), | 494 start_reg_(start_reg), |
| 452 end_reg_(end_reg) { } | 495 end_reg_(end_reg) { } |
| 453 virtual void Accept(NodeVisitor* visitor); | 496 virtual void Accept(NodeVisitor* visitor); |
| 454 RegExpNode* on_failure() { return on_failure_; } | 497 RegExpNode* on_failure() { return on_failure_; } |
| 455 int start_register() { return start_reg_; } | 498 int start_register() { return start_reg_; } |
| 456 int end_register() { return end_reg_; } | 499 int end_register() { return end_reg_; } |
| 457 virtual void Emit(RegExpCompiler* compiler) { UNREACHABLE(); } | 500 virtual bool Emit(RegExpCompiler* compiler) { return false; } |
| 458 private: | 501 private: |
| 459 RegExpNode* on_failure_; | 502 RegExpNode* on_failure_; |
| 460 int start_reg_; | 503 int start_reg_; |
| 461 int end_reg_; | 504 int end_reg_; |
| 462 }; | 505 }; |
| 463 | 506 |
| 464 | 507 |
| 465 class CharacterClassNode: public SeqRegExpNode { | 508 class CharacterClassNode: public SeqRegExpNode { |
| 466 public: | 509 public: |
| 467 CharacterClassNode(ZoneList<CharacterRange>* ranges, | 510 CharacterClassNode(ZoneList<CharacterRange>* ranges, |
| 468 bool is_negated, | 511 bool is_negated, |
| 469 RegExpNode* on_success, | 512 RegExpNode* on_success, |
| 470 RegExpNode* on_failure) | 513 RegExpNode* on_failure) |
| 471 : SeqRegExpNode(on_success), | 514 : SeqRegExpNode(on_success), |
| 472 on_failure_(on_failure), | 515 on_failure_(on_failure), |
| 473 ranges_(ranges), | 516 ranges_(ranges), |
| 474 is_negated_(is_negated ) { } | 517 is_negated_(is_negated ) { } |
| 475 virtual void Accept(NodeVisitor* visitor); | 518 virtual void Accept(NodeVisitor* visitor); |
| 476 ZoneList<CharacterRange>* ranges() { return ranges_; } | 519 ZoneList<CharacterRange>* ranges() { return ranges_; } |
| 477 bool is_negated() { return is_negated_; } | 520 bool is_negated() { return is_negated_; } |
| 478 RegExpNode* on_failure() { return on_failure_; } | 521 RegExpNode* on_failure() { return on_failure_; } |
| 479 virtual void Emit(RegExpCompiler* compiler) { UNREACHABLE(); } | 522 virtual bool Emit(RegExpCompiler* compiler) { return false; } |
| 480 static void AddInverseToTable(ZoneList<CharacterRange>* ranges, | 523 static void AddInverseToTable(ZoneList<CharacterRange>* ranges, |
| 481 DispatchTable* table, | 524 DispatchTable* table, |
| 482 int index); | 525 int index); |
| 483 private: | 526 private: |
| 484 RegExpNode* on_failure_; | 527 RegExpNode* on_failure_; |
| 485 ZoneList<CharacterRange>* ranges_; | 528 ZoneList<CharacterRange>* ranges_; |
| 486 bool is_negated_; | 529 bool is_negated_; |
| 487 }; | 530 }; |
| 488 | 531 |
| 489 | 532 |
| 490 class EndNode: public RegExpNode { | 533 class EndNode: public RegExpNode { |
| 491 public: | 534 public: |
| 492 enum Action { ACCEPT, BACKTRACK }; | 535 enum Action { ACCEPT, BACKTRACK }; |
| 493 virtual void Accept(NodeVisitor* visitor); | 536 virtual void Accept(NodeVisitor* visitor); |
| 494 static EndNode* GetAccept() { return &kAccept; } | 537 static EndNode* GetAccept() { return &kAccept; } |
| 495 static EndNode* GetBacktrack() { return &kBacktrack; } | 538 static EndNode* GetBacktrack() { return &kBacktrack; } |
| 496 virtual void Emit(RegExpCompiler* compiler) { UNREACHABLE(); } | 539 virtual bool Emit(RegExpCompiler* compiler); |
| 497 private: | 540 private: |
| 498 explicit EndNode(Action action) : action_(action) { } | 541 explicit EndNode(Action action) : action_(action) { } |
| 499 Action action_; | 542 Action action_; |
| 500 static EndNode kAccept; | 543 static EndNode kAccept; |
| 501 static EndNode kBacktrack; | 544 static EndNode kBacktrack; |
| 502 }; | 545 }; |
| 503 | 546 |
| 504 | 547 |
| 505 class Guard: public ZoneObject { | 548 class Guard: public ZoneObject { |
| 506 public: | 549 public: |
| (...skipping 28 matching lines...) Expand all Loading... |
| 535 public: | 578 public: |
| 536 explicit ChoiceNode(int expected_size, RegExpNode* on_failure) | 579 explicit ChoiceNode(int expected_size, RegExpNode* on_failure) |
| 537 : on_failure_(on_failure), | 580 : on_failure_(on_failure), |
| 538 choices_(new ZoneList<GuardedAlternative>(expected_size)), | 581 choices_(new ZoneList<GuardedAlternative>(expected_size)), |
| 539 visited_(false) { } | 582 visited_(false) { } |
| 540 virtual void Accept(NodeVisitor* visitor); | 583 virtual void Accept(NodeVisitor* visitor); |
| 541 void AddChild(GuardedAlternative node) { choices()->Add(node); } | 584 void AddChild(GuardedAlternative node) { choices()->Add(node); } |
| 542 ZoneList<GuardedAlternative>* choices() { return choices_; } | 585 ZoneList<GuardedAlternative>* choices() { return choices_; } |
| 543 DispatchTable* table() { return &table_; } | 586 DispatchTable* table() { return &table_; } |
| 544 RegExpNode* on_failure() { return on_failure_; } | 587 RegExpNode* on_failure() { return on_failure_; } |
| 545 virtual void Emit(RegExpCompiler* compiler); | 588 virtual bool Emit(RegExpCompiler* compiler); |
| 546 bool visited() { return visited_; } | 589 bool visited() { return visited_; } |
| 547 void set_visited(bool value) { visited_ = value; } | 590 void set_visited(bool value) { visited_ = value; } |
| 548 private: | 591 private: |
| 549 RegExpNode* on_failure_; | 592 RegExpNode* on_failure_; |
| 550 ZoneList<GuardedAlternative>* choices_; | 593 ZoneList<GuardedAlternative>* choices_; |
| 551 DispatchTable table_; | 594 DispatchTable table_; |
| 552 bool visited_; | 595 bool visited_; |
| 553 }; | 596 }; |
| 554 | 597 |
| 555 | 598 |
| 556 struct RegExpParseResult { | 599 struct RegExpParseResult { |
| 557 RegExpTree* tree; | 600 RegExpTree* tree; |
| 558 bool has_character_escapes; | 601 bool has_character_escapes; |
| 559 Handle<String> error; | 602 Handle<String> error; |
| 560 int capture_count; | 603 int capture_count; |
| 561 }; | 604 }; |
| 562 | 605 |
| 563 | 606 |
| 564 class RegExpEngine: public AllStatic { | 607 class RegExpEngine: public AllStatic { |
| 565 public: | 608 public: |
| 566 static RegExpNode* Compile(RegExpParseResult* input); | 609 static Handle<FixedArray> Compile(RegExpParseResult* input, |
| 610 RegExpNode** node_return); |
| 567 static void DotPrint(const char* label, RegExpNode* node); | 611 static void DotPrint(const char* label, RegExpNode* node); |
| 568 }; | 612 }; |
| 569 | 613 |
| 570 | 614 |
| 571 class RegExpCompiler; | 615 class RegExpCompiler; |
| 572 | 616 |
| 573 | 617 |
| 574 } } // namespace v8::internal | 618 } } // namespace v8::internal |
| 575 | 619 |
| 576 #endif // V8_JSREGEXP_H_ | 620 #endif // V8_JSREGEXP_H_ |
| OLD | NEW |