LCOV - code coverage report
Current view: top level - src/builtins - builtins-regexp.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 43 43 100.0 %
Date: 2017-04-26 Functions: 32 48 66.7 %

          Line data    Source code
       1             : // Copyright 2016 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/builtins/builtins-utils.h"
       6             : #include "src/builtins/builtins.h"
       7             : #include "src/counters.h"
       8             : #include "src/objects-inl.h"
       9             : #include "src/regexp/jsregexp.h"
      10             : #include "src/regexp/regexp-utils.h"
      11             : #include "src/string-builder.h"
      12             : 
      13             : namespace v8 {
      14             : namespace internal {
      15             : 
      16             : // -----------------------------------------------------------------------------
      17             : // ES6 section 21.2 RegExp Objects
      18             : 
      19    13516425 : BUILTIN(RegExpPrototypeToString) {
      20             :   HandleScope scope(isolate);
      21     4506657 :   CHECK_RECEIVER(JSReceiver, recv, "RegExp.prototype.toString");
      22             : 
      23     9010162 :   if (*recv == isolate->regexp_function()->prototype()) {
      24          49 :     isolate->CountUsage(v8::Isolate::kRegExpPrototypeToString);
      25             :   }
      26             : 
      27     4505081 :   IncrementalStringBuilder builder(isolate);
      28             : 
      29             :   builder.AppendCharacter('/');
      30             :   {
      31             :     Handle<Object> source;
      32     9010162 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
      33             :         isolate, source,
      34             :         JSReceiver::GetProperty(recv, isolate->factory()->source_string()));
      35             :     Handle<String> source_str;
      36     9010162 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, source_str,
      37             :                                        Object::ToString(isolate, source));
      38     4505081 :     builder.AppendString(source_str);
      39             :   }
      40             : 
      41             :   builder.AppendCharacter('/');
      42             :   {
      43             :     Handle<Object> flags;
      44     9010162 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
      45             :         isolate, flags,
      46             :         JSReceiver::GetProperty(recv, isolate->factory()->flags_string()));
      47             :     Handle<String> flags_str;
      48     9010162 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, flags_str,
      49             :                                        Object::ToString(isolate, flags));
      50     4505081 :     builder.AppendString(flags_str);
      51             :   }
      52             : 
      53    13515243 :   RETURN_RESULT_OR_FAILURE(isolate, builder.Finish());
      54             : }
      55             : 
      56             : // The properties $1..$9 are the first nine capturing substrings of the last
      57             : // successful match, or ''.  The function RegExpMakeCaptureGetter will be
      58             : // called with indices from 1 to 9.
      59             : #define DEFINE_CAPTURE_GETTER(i)                        \
      60             :   BUILTIN(RegExpCapture##i##Getter) {                   \
      61             :     HandleScope scope(isolate);                         \
      62             :     return *RegExpUtils::GenericCaptureGetter(          \
      63             :         isolate, isolate->regexp_last_match_info(), i); \
      64             :   }
      65     1210878 : DEFINE_CAPTURE_GETTER(1)
      66        7122 : DEFINE_CAPTURE_GETTER(2)
      67        7032 : DEFINE_CAPTURE_GETTER(3)
      68        6690 : DEFINE_CAPTURE_GETTER(4)
      69        6768 : DEFINE_CAPTURE_GETTER(5)
      70        6510 : DEFINE_CAPTURE_GETTER(6)
      71        6504 : DEFINE_CAPTURE_GETTER(7)
      72        6246 : DEFINE_CAPTURE_GETTER(8)
      73        6246 : DEFINE_CAPTURE_GETTER(9)
      74             : #undef DEFINE_CAPTURE_GETTER
      75             : 
      76             : // The properties `input` and `$_` are aliases for each other.  When this
      77             : // value is set, the value it is set to is coerced to a string.
      78             : // Getter and setter for the input.
      79             : 
      80       46488 : BUILTIN(RegExpInputGetter) {
      81             :   HandleScope scope(isolate);
      82       30992 :   Handle<Object> obj(isolate->regexp_last_match_info()->LastInput(), isolate);
      83          14 :   return obj->IsUndefined(isolate) ? isolate->heap()->empty_string()
      84       30992 :                                    : String::cast(*obj);
      85             : }
      86             : 
      87         213 : BUILTIN(RegExpInputSetter) {
      88             :   HandleScope scope(isolate);
      89          71 :   Handle<Object> value = args.atOrUndefined(isolate, 1);
      90             :   Handle<String> str;
      91         142 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, str,
      92             :                                      Object::ToString(isolate, value));
      93         142 :   isolate->regexp_last_match_info()->SetLastInput(*str);
      94          71 :   return isolate->heap()->undefined_value();
      95             : }
      96             : 
      97             : // Getters for the static properties lastMatch, lastParen, leftContext, and
      98             : // rightContext of the RegExp constructor.  The properties are computed based
      99             : // on the captures array of the last successful match and the subject string
     100             : // of the last successful match.
     101      602157 : BUILTIN(RegExpLastMatchGetter) {
     102             :   HandleScope scope(isolate);
     103             :   return *RegExpUtils::GenericCaptureGetter(
     104      602157 :       isolate, isolate->regexp_last_match_info(), 0);
     105             : }
     106             : 
     107        3747 : BUILTIN(RegExpLastParenGetter) {
     108             :   HandleScope scope(isolate);
     109        1249 :   Handle<RegExpMatchInfo> match_info = isolate->regexp_last_match_info();
     110             :   const int length = match_info->NumberOfCaptureRegisters();
     111        1249 :   if (length <= 2) return isolate->heap()->empty_string();  // No captures.
     112             : 
     113             :   DCHECK_EQ(0, length % 2);
     114         968 :   const int last_capture = (length / 2) - 1;
     115             : 
     116             :   // We match the SpiderMonkey behavior: return the substring defined by the
     117             :   // last pair (after the first pair) of elements of the capture array even if
     118             :   // it is empty.
     119        1936 :   return *RegExpUtils::GenericCaptureGetter(isolate, match_info, last_capture);
     120             : }
     121             : 
     122      600123 : BUILTIN(RegExpLeftContextGetter) {
     123             :   HandleScope scope(isolate);
     124      200041 :   Handle<RegExpMatchInfo> match_info = isolate->regexp_last_match_info();
     125             :   const int start_index = match_info->Capture(0);
     126             :   Handle<String> last_subject(match_info->LastSubject());
     127      600123 :   return *isolate->factory()->NewSubString(last_subject, 0, start_index);
     128             : }
     129             : 
     130       47028 : BUILTIN(RegExpRightContextGetter) {
     131             :   HandleScope scope(isolate);
     132       15676 :   Handle<RegExpMatchInfo> match_info = isolate->regexp_last_match_info();
     133             :   const int start_index = match_info->Capture(1);
     134             :   Handle<String> last_subject(match_info->LastSubject());
     135             :   const int len = last_subject->length();
     136       47028 :   return *isolate->factory()->NewSubString(last_subject, start_index, len);
     137             : }
     138             : 
     139             : }  // namespace internal
     140             : }  // namespace v8

Generated by: LCOV version 1.10