v8  3.25.30(node0.11.13)
V8 is Google's open source JavaScript engine
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
interpreter-irregexp.cc
Go to the documentation of this file.
1 // Copyright 2011 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are
4 // met:
5 //
6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided
11 // with the distribution.
12 // * Neither the name of Google Inc. nor the names of its
13 // contributors may be used to endorse or promote products derived
14 // from this software without specific prior written permission.
15 //
16 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 
28 // A simple interpreter for the Irregexp byte code.
29 
30 
31 #include "v8.h"
32 #include "unicode.h"
33 #include "utils.h"
34 #include "ast.h"
35 #include "bytecodes-irregexp.h"
36 #include "interpreter-irregexp.h"
37 #include "jsregexp.h"
38 #include "regexp-macro-assembler.h"
39 
40 namespace v8 {
41 namespace internal {
42 
43 
45 
46 static bool BackRefMatchesNoCase(Canonicalize* interp_canonicalize,
47  int from,
48  int current,
49  int len,
50  Vector<const uc16> subject) {
51  for (int i = 0; i < len; i++) {
52  unibrow::uchar old_char = subject[from++];
53  unibrow::uchar new_char = subject[current++];
54  if (old_char == new_char) continue;
55  unibrow::uchar old_string[1] = { old_char };
56  unibrow::uchar new_string[1] = { new_char };
57  interp_canonicalize->get(old_char, '\0', old_string);
58  interp_canonicalize->get(new_char, '\0', new_string);
59  if (old_string[0] != new_string[0]) {
60  return false;
61  }
62  }
63  return true;
64 }
65 
66 
67 static bool BackRefMatchesNoCase(Canonicalize* interp_canonicalize,
68  int from,
69  int current,
70  int len,
71  Vector<const uint8_t> subject) {
72  for (int i = 0; i < len; i++) {
73  unsigned int old_char = subject[from++];
74  unsigned int new_char = subject[current++];
75  if (old_char == new_char) continue;
76  // Convert both characters to lower case.
77  old_char |= 0x20;
78  new_char |= 0x20;
79  if (old_char != new_char) return false;
80  // Not letters in the ASCII range and Latin-1 range.
81  if (!(old_char - 'a' <= 'z' - 'a') &&
82  !(old_char - 224 <= 254 - 224 && old_char != 247)) {
83  return false;
84  }
85  }
86  return true;
87 }
88 
89 
90 #ifdef DEBUG
91 static void TraceInterpreter(const byte* code_base,
92  const byte* pc,
93  int stack_depth,
94  int current_position,
95  uint32_t current_char,
96  int bytecode_length,
97  const char* bytecode_name) {
98  if (FLAG_trace_regexp_bytecodes) {
99  bool printable = (current_char < 127 && current_char >= 32);
100  const char* format =
101  printable ?
102  "pc = %02x, sp = %d, curpos = %d, curchar = %08x (%c), bc = %s" :
103  "pc = %02x, sp = %d, curpos = %d, curchar = %08x .%c., bc = %s";
104  PrintF(format,
105  pc - code_base,
106  stack_depth,
107  current_position,
108  current_char,
109  printable ? current_char : '.',
110  bytecode_name);
111  for (int i = 0; i < bytecode_length; i++) {
112  printf(", %02x", pc[i]);
113  }
114  printf(" ");
115  for (int i = 1; i < bytecode_length; i++) {
116  unsigned char b = pc[i];
117  if (b < 127 && b >= 32) {
118  printf("%c", b);
119  } else {
120  printf(".");
121  }
122  }
123  printf("\n");
124  }
125 }
126 
127 
128 #define BYTECODE(name) \
129  case BC_##name: \
130  TraceInterpreter(code_base, \
131  pc, \
132  static_cast<int>(backtrack_sp - backtrack_stack_base), \
133  current, \
134  current_char, \
135  BC_##name##_LENGTH, \
136  #name);
137 #else
138 #define BYTECODE(name) \
139  case BC_##name:
140 #endif
141 
142 
143 static int32_t Load32Aligned(const byte* pc) {
144  ASSERT((reinterpret_cast<intptr_t>(pc) & 3) == 0);
145  return *reinterpret_cast<const int32_t *>(pc);
146 }
147 
148 
149 static int32_t Load16Aligned(const byte* pc) {
150  ASSERT((reinterpret_cast<intptr_t>(pc) & 1) == 0);
151  return *reinterpret_cast<const uint16_t *>(pc);
152 }
153 
154 
155 // A simple abstraction over the backtracking stack used by the interpreter.
156 // This backtracking stack does not grow automatically, but it ensures that the
157 // the memory held by the stack is released or remembered in a cache if the
158 // matching terminates.
160  public:
161  explicit BacktrackStack() {
162  data_ = NewArray<int>(kBacktrackStackSize);
163  }
164 
166  DeleteArray(data_);
167  }
168 
169  int* data() const { return data_; }
170 
171  int max_size() const { return kBacktrackStackSize; }
172 
173  private:
174  static const int kBacktrackStackSize = 10000;
175 
176  int* data_;
177 
178  DISALLOW_COPY_AND_ASSIGN(BacktrackStack);
179 };
180 
181 
182 template <typename Char>
183 static RegExpImpl::IrregexpResult RawMatch(Isolate* isolate,
184  const byte* code_base,
185  Vector<const Char> subject,
186  int* registers,
187  int current,
188  uint32_t current_char) {
189  const byte* pc = code_base;
190  // BacktrackStack ensures that the memory allocated for the backtracking stack
191  // is returned to the system or cached if there is no stack being cached at
192  // the moment.
193  BacktrackStack backtrack_stack;
194  int* backtrack_stack_base = backtrack_stack.data();
195  int* backtrack_sp = backtrack_stack_base;
196  int backtrack_stack_space = backtrack_stack.max_size();
197 #ifdef DEBUG
198  if (FLAG_trace_regexp_bytecodes) {
199  PrintF("\n\nStart bytecode interpreter\n\n");
200  }
201 #endif
202  while (true) {
203  int32_t insn = Load32Aligned(pc);
204  switch (insn & BYTECODE_MASK) {
205  BYTECODE(BREAK)
206  UNREACHABLE();
207  return RegExpImpl::RE_FAILURE;
208  BYTECODE(PUSH_CP)
209  if (--backtrack_stack_space < 0) {
211  }
212  *backtrack_sp++ = current;
213  pc += BC_PUSH_CP_LENGTH;
214  break;
215  BYTECODE(PUSH_BT)
216  if (--backtrack_stack_space < 0) {
218  }
219  *backtrack_sp++ = Load32Aligned(pc + 4);
220  pc += BC_PUSH_BT_LENGTH;
221  break;
222  BYTECODE(PUSH_REGISTER)
223  if (--backtrack_stack_space < 0) {
225  }
226  *backtrack_sp++ = registers[insn >> BYTECODE_SHIFT];
227  pc += BC_PUSH_REGISTER_LENGTH;
228  break;
229  BYTECODE(SET_REGISTER)
230  registers[insn >> BYTECODE_SHIFT] = Load32Aligned(pc + 4);
231  pc += BC_SET_REGISTER_LENGTH;
232  break;
233  BYTECODE(ADVANCE_REGISTER)
234  registers[insn >> BYTECODE_SHIFT] += Load32Aligned(pc + 4);
235  pc += BC_ADVANCE_REGISTER_LENGTH;
236  break;
237  BYTECODE(SET_REGISTER_TO_CP)
238  registers[insn >> BYTECODE_SHIFT] = current + Load32Aligned(pc + 4);
239  pc += BC_SET_REGISTER_TO_CP_LENGTH;
240  break;
241  BYTECODE(SET_CP_TO_REGISTER)
242  current = registers[insn >> BYTECODE_SHIFT];
243  pc += BC_SET_CP_TO_REGISTER_LENGTH;
244  break;
245  BYTECODE(SET_REGISTER_TO_SP)
246  registers[insn >> BYTECODE_SHIFT] =
247  static_cast<int>(backtrack_sp - backtrack_stack_base);
248  pc += BC_SET_REGISTER_TO_SP_LENGTH;
249  break;
250  BYTECODE(SET_SP_TO_REGISTER)
251  backtrack_sp = backtrack_stack_base + registers[insn >> BYTECODE_SHIFT];
252  backtrack_stack_space = backtrack_stack.max_size() -
253  static_cast<int>(backtrack_sp - backtrack_stack_base);
254  pc += BC_SET_SP_TO_REGISTER_LENGTH;
255  break;
256  BYTECODE(POP_CP)
257  backtrack_stack_space++;
258  --backtrack_sp;
259  current = *backtrack_sp;
260  pc += BC_POP_CP_LENGTH;
261  break;
262  BYTECODE(POP_BT)
263  backtrack_stack_space++;
264  --backtrack_sp;
265  pc = code_base + *backtrack_sp;
266  break;
267  BYTECODE(POP_REGISTER)
268  backtrack_stack_space++;
269  --backtrack_sp;
270  registers[insn >> BYTECODE_SHIFT] = *backtrack_sp;
271  pc += BC_POP_REGISTER_LENGTH;
272  break;
273  BYTECODE(FAIL)
274  return RegExpImpl::RE_FAILURE;
275  BYTECODE(SUCCEED)
276  return RegExpImpl::RE_SUCCESS;
277  BYTECODE(ADVANCE_CP)
278  current += insn >> BYTECODE_SHIFT;
279  pc += BC_ADVANCE_CP_LENGTH;
280  break;
281  BYTECODE(GOTO)
282  pc = code_base + Load32Aligned(pc + 4);
283  break;
284  BYTECODE(ADVANCE_CP_AND_GOTO)
285  current += insn >> BYTECODE_SHIFT;
286  pc = code_base + Load32Aligned(pc + 4);
287  break;
288  BYTECODE(CHECK_GREEDY)
289  if (current == backtrack_sp[-1]) {
290  backtrack_sp--;
291  backtrack_stack_space++;
292  pc = code_base + Load32Aligned(pc + 4);
293  } else {
294  pc += BC_CHECK_GREEDY_LENGTH;
295  }
296  break;
297  BYTECODE(LOAD_CURRENT_CHAR) {
298  int pos = current + (insn >> BYTECODE_SHIFT);
299  if (pos >= subject.length()) {
300  pc = code_base + Load32Aligned(pc + 4);
301  } else {
302  current_char = subject[pos];
303  pc += BC_LOAD_CURRENT_CHAR_LENGTH;
304  }
305  break;
306  }
307  BYTECODE(LOAD_CURRENT_CHAR_UNCHECKED) {
308  int pos = current + (insn >> BYTECODE_SHIFT);
309  current_char = subject[pos];
310  pc += BC_LOAD_CURRENT_CHAR_UNCHECKED_LENGTH;
311  break;
312  }
313  BYTECODE(LOAD_2_CURRENT_CHARS) {
314  int pos = current + (insn >> BYTECODE_SHIFT);
315  if (pos + 2 > subject.length()) {
316  pc = code_base + Load32Aligned(pc + 4);
317  } else {
318  Char next = subject[pos + 1];
319  current_char =
320  (subject[pos] | (next << (kBitsPerByte * sizeof(Char))));
321  pc += BC_LOAD_2_CURRENT_CHARS_LENGTH;
322  }
323  break;
324  }
325  BYTECODE(LOAD_2_CURRENT_CHARS_UNCHECKED) {
326  int pos = current + (insn >> BYTECODE_SHIFT);
327  Char next = subject[pos + 1];
328  current_char = (subject[pos] | (next << (kBitsPerByte * sizeof(Char))));
329  pc += BC_LOAD_2_CURRENT_CHARS_UNCHECKED_LENGTH;
330  break;
331  }
332  BYTECODE(LOAD_4_CURRENT_CHARS) {
333  ASSERT(sizeof(Char) == 1);
334  int pos = current + (insn >> BYTECODE_SHIFT);
335  if (pos + 4 > subject.length()) {
336  pc = code_base + Load32Aligned(pc + 4);
337  } else {
338  Char next1 = subject[pos + 1];
339  Char next2 = subject[pos + 2];
340  Char next3 = subject[pos + 3];
341  current_char = (subject[pos] |
342  (next1 << 8) |
343  (next2 << 16) |
344  (next3 << 24));
345  pc += BC_LOAD_4_CURRENT_CHARS_LENGTH;
346  }
347  break;
348  }
349  BYTECODE(LOAD_4_CURRENT_CHARS_UNCHECKED) {
350  ASSERT(sizeof(Char) == 1);
351  int pos = current + (insn >> BYTECODE_SHIFT);
352  Char next1 = subject[pos + 1];
353  Char next2 = subject[pos + 2];
354  Char next3 = subject[pos + 3];
355  current_char = (subject[pos] |
356  (next1 << 8) |
357  (next2 << 16) |
358  (next3 << 24));
359  pc += BC_LOAD_4_CURRENT_CHARS_UNCHECKED_LENGTH;
360  break;
361  }
362  BYTECODE(CHECK_4_CHARS) {
363  uint32_t c = Load32Aligned(pc + 4);
364  if (c == current_char) {
365  pc = code_base + Load32Aligned(pc + 8);
366  } else {
367  pc += BC_CHECK_4_CHARS_LENGTH;
368  }
369  break;
370  }
371  BYTECODE(CHECK_CHAR) {
372  uint32_t c = (insn >> BYTECODE_SHIFT);
373  if (c == current_char) {
374  pc = code_base + Load32Aligned(pc + 4);
375  } else {
376  pc += BC_CHECK_CHAR_LENGTH;
377  }
378  break;
379  }
380  BYTECODE(CHECK_NOT_4_CHARS) {
381  uint32_t c = Load32Aligned(pc + 4);
382  if (c != current_char) {
383  pc = code_base + Load32Aligned(pc + 8);
384  } else {
385  pc += BC_CHECK_NOT_4_CHARS_LENGTH;
386  }
387  break;
388  }
389  BYTECODE(CHECK_NOT_CHAR) {
390  uint32_t c = (insn >> BYTECODE_SHIFT);
391  if (c != current_char) {
392  pc = code_base + Load32Aligned(pc + 4);
393  } else {
394  pc += BC_CHECK_NOT_CHAR_LENGTH;
395  }
396  break;
397  }
398  BYTECODE(AND_CHECK_4_CHARS) {
399  uint32_t c = Load32Aligned(pc + 4);
400  if (c == (current_char & Load32Aligned(pc + 8))) {
401  pc = code_base + Load32Aligned(pc + 12);
402  } else {
403  pc += BC_AND_CHECK_4_CHARS_LENGTH;
404  }
405  break;
406  }
407  BYTECODE(AND_CHECK_CHAR) {
408  uint32_t c = (insn >> BYTECODE_SHIFT);
409  if (c == (current_char & Load32Aligned(pc + 4))) {
410  pc = code_base + Load32Aligned(pc + 8);
411  } else {
412  pc += BC_AND_CHECK_CHAR_LENGTH;
413  }
414  break;
415  }
416  BYTECODE(AND_CHECK_NOT_4_CHARS) {
417  uint32_t c = Load32Aligned(pc + 4);
418  if (c != (current_char & Load32Aligned(pc + 8))) {
419  pc = code_base + Load32Aligned(pc + 12);
420  } else {
421  pc += BC_AND_CHECK_NOT_4_CHARS_LENGTH;
422  }
423  break;
424  }
425  BYTECODE(AND_CHECK_NOT_CHAR) {
426  uint32_t c = (insn >> BYTECODE_SHIFT);
427  if (c != (current_char & Load32Aligned(pc + 4))) {
428  pc = code_base + Load32Aligned(pc + 8);
429  } else {
430  pc += BC_AND_CHECK_NOT_CHAR_LENGTH;
431  }
432  break;
433  }
434  BYTECODE(MINUS_AND_CHECK_NOT_CHAR) {
435  uint32_t c = (insn >> BYTECODE_SHIFT);
436  uint32_t minus = Load16Aligned(pc + 4);
437  uint32_t mask = Load16Aligned(pc + 6);
438  if (c != ((current_char - minus) & mask)) {
439  pc = code_base + Load32Aligned(pc + 8);
440  } else {
441  pc += BC_MINUS_AND_CHECK_NOT_CHAR_LENGTH;
442  }
443  break;
444  }
445  BYTECODE(CHECK_CHAR_IN_RANGE) {
446  uint32_t from = Load16Aligned(pc + 4);
447  uint32_t to = Load16Aligned(pc + 6);
448  if (from <= current_char && current_char <= to) {
449  pc = code_base + Load32Aligned(pc + 8);
450  } else {
451  pc += BC_CHECK_CHAR_IN_RANGE_LENGTH;
452  }
453  break;
454  }
455  BYTECODE(CHECK_CHAR_NOT_IN_RANGE) {
456  uint32_t from = Load16Aligned(pc + 4);
457  uint32_t to = Load16Aligned(pc + 6);
458  if (from > current_char || current_char > to) {
459  pc = code_base + Load32Aligned(pc + 8);
460  } else {
461  pc += BC_CHECK_CHAR_NOT_IN_RANGE_LENGTH;
462  }
463  break;
464  }
465  BYTECODE(CHECK_BIT_IN_TABLE) {
467  byte b = pc[8 + ((current_char & mask) >> kBitsPerByteLog2)];
468  int bit = (current_char & (kBitsPerByte - 1));
469  if ((b & (1 << bit)) != 0) {
470  pc = code_base + Load32Aligned(pc + 4);
471  } else {
472  pc += BC_CHECK_BIT_IN_TABLE_LENGTH;
473  }
474  break;
475  }
476  BYTECODE(CHECK_LT) {
477  uint32_t limit = (insn >> BYTECODE_SHIFT);
478  if (current_char < limit) {
479  pc = code_base + Load32Aligned(pc + 4);
480  } else {
481  pc += BC_CHECK_LT_LENGTH;
482  }
483  break;
484  }
485  BYTECODE(CHECK_GT) {
486  uint32_t limit = (insn >> BYTECODE_SHIFT);
487  if (current_char > limit) {
488  pc = code_base + Load32Aligned(pc + 4);
489  } else {
490  pc += BC_CHECK_GT_LENGTH;
491  }
492  break;
493  }
494  BYTECODE(CHECK_REGISTER_LT)
495  if (registers[insn >> BYTECODE_SHIFT] < Load32Aligned(pc + 4)) {
496  pc = code_base + Load32Aligned(pc + 8);
497  } else {
498  pc += BC_CHECK_REGISTER_LT_LENGTH;
499  }
500  break;
501  BYTECODE(CHECK_REGISTER_GE)
502  if (registers[insn >> BYTECODE_SHIFT] >= Load32Aligned(pc + 4)) {
503  pc = code_base + Load32Aligned(pc + 8);
504  } else {
505  pc += BC_CHECK_REGISTER_GE_LENGTH;
506  }
507  break;
508  BYTECODE(CHECK_REGISTER_EQ_POS)
509  if (registers[insn >> BYTECODE_SHIFT] == current) {
510  pc = code_base + Load32Aligned(pc + 4);
511  } else {
512  pc += BC_CHECK_REGISTER_EQ_POS_LENGTH;
513  }
514  break;
515  BYTECODE(CHECK_NOT_REGS_EQUAL)
516  if (registers[insn >> BYTECODE_SHIFT] ==
517  registers[Load32Aligned(pc + 4)]) {
518  pc += BC_CHECK_NOT_REGS_EQUAL_LENGTH;
519  } else {
520  pc = code_base + Load32Aligned(pc + 8);
521  }
522  break;
523  BYTECODE(CHECK_NOT_BACK_REF) {
524  int from = registers[insn >> BYTECODE_SHIFT];
525  int len = registers[(insn >> BYTECODE_SHIFT) + 1] - from;
526  if (from < 0 || len <= 0) {
527  pc += BC_CHECK_NOT_BACK_REF_LENGTH;
528  break;
529  }
530  if (current + len > subject.length()) {
531  pc = code_base + Load32Aligned(pc + 4);
532  break;
533  } else {
534  int i;
535  for (i = 0; i < len; i++) {
536  if (subject[from + i] != subject[current + i]) {
537  pc = code_base + Load32Aligned(pc + 4);
538  break;
539  }
540  }
541  if (i < len) break;
542  current += len;
543  }
544  pc += BC_CHECK_NOT_BACK_REF_LENGTH;
545  break;
546  }
547  BYTECODE(CHECK_NOT_BACK_REF_NO_CASE) {
548  int from = registers[insn >> BYTECODE_SHIFT];
549  int len = registers[(insn >> BYTECODE_SHIFT) + 1] - from;
550  if (from < 0 || len <= 0) {
551  pc += BC_CHECK_NOT_BACK_REF_NO_CASE_LENGTH;
552  break;
553  }
554  if (current + len > subject.length()) {
555  pc = code_base + Load32Aligned(pc + 4);
556  break;
557  } else {
558  if (BackRefMatchesNoCase(isolate->interp_canonicalize_mapping(),
559  from, current, len, subject)) {
560  current += len;
561  pc += BC_CHECK_NOT_BACK_REF_NO_CASE_LENGTH;
562  } else {
563  pc = code_base + Load32Aligned(pc + 4);
564  }
565  }
566  break;
567  }
568  BYTECODE(CHECK_AT_START)
569  if (current == 0) {
570  pc = code_base + Load32Aligned(pc + 4);
571  } else {
572  pc += BC_CHECK_AT_START_LENGTH;
573  }
574  break;
575  BYTECODE(CHECK_NOT_AT_START)
576  if (current == 0) {
577  pc += BC_CHECK_NOT_AT_START_LENGTH;
578  } else {
579  pc = code_base + Load32Aligned(pc + 4);
580  }
581  break;
582  BYTECODE(SET_CURRENT_POSITION_FROM_END) {
583  int by = static_cast<uint32_t>(insn) >> BYTECODE_SHIFT;
584  if (subject.length() - current > by) {
585  current = subject.length() - by;
586  current_char = subject[current - 1];
587  }
588  pc += BC_SET_CURRENT_POSITION_FROM_END_LENGTH;
589  break;
590  }
591  default:
592  UNREACHABLE();
593  break;
594  }
595  }
596 }
597 
598 
600  Isolate* isolate,
601  Handle<ByteArray> code_array,
602  Handle<String> subject,
603  int* registers,
604  int start_position) {
605  ASSERT(subject->IsFlat());
606 
608  const byte* code_base = code_array->GetDataStartAddress();
609  uc16 previous_char = '\n';
610  String::FlatContent subject_content = subject->GetFlatContent();
611  if (subject_content.IsAscii()) {
612  Vector<const uint8_t> subject_vector = subject_content.ToOneByteVector();
613  if (start_position != 0) previous_char = subject_vector[start_position - 1];
614  return RawMatch(isolate,
615  code_base,
616  subject_vector,
617  registers,
618  start_position,
619  previous_char);
620  } else {
621  ASSERT(subject_content.IsTwoByte());
622  Vector<const uc16> subject_vector = subject_content.ToUC16Vector();
623  if (start_position != 0) previous_char = subject_vector[start_position - 1];
624  return RawMatch(isolate,
625  code_base,
626  subject_vector,
627  registers,
628  start_position,
629  previous_char);
630  }
631 }
632 
633 } } // namespace v8::internal
void PrintF(const char *format,...)
Definition: v8utils.cc:40
#define CHECK_GT(a, b)
Definition: checks.h:260
int int32_t
Definition: unicode.cc:47
const int kBitsPerByteLog2
Definition: globals.h:288
#define CHECK_LT(a, b)
Definition: checks.h:262
unibrow::Mapping< unibrow::Ecma262Canonicalize > Canonicalize
const int BYTECODE_MASK
#define ASSERT(condition)
Definition: checks.h:329
unsigned short uint16_t
Definition: unicode.cc:46
int get(uchar c, uchar n, uchar *result)
Definition: unicode-inl.h:50
uint8_t byte
Definition: globals.h:185
#define UNREACHABLE()
Definition: checks.h:52
static RegExpImpl::IrregexpResult Match(Isolate *isolate, Handle< ByteArray > code, Handle< String > subject, int *captures, int start_position)
const Register pc
Vector< const uc16 > ToUC16Vector()
Definition: objects.h:8757
const int kBitsPerByte
Definition: globals.h:287
uint16_t uc16
Definition: globals.h:309
Vector< const uint8_t > ToOneByteVector()
Definition: objects.h:8751
void DeleteArray(T *array)
Definition: allocation.h:91
const int BYTECODE_SHIFT
#define BYTECODE(name)
unsigned int uchar
Definition: unicode.h:40