blob: ca15864fec42f62a5bd222ced1ac98e9ce138b13 [file] [log] [blame]
Howard Hinnant3257c982010-06-17 00:34:59 +00001// -*- C++ -*-
2//===--------------------------- regex ------------------------------------===//
3//
4// The LLVM Compiler Infrastructure
5//
6// This file is distributed under the University of Illinois Open Source
7// License. See LICENSE.TXT for details.
8//
9//===----------------------------------------------------------------------===//
10
11#ifndef _LIBCPP_REGEX
12#define _LIBCPP_REGEX
13
14/*
15 regex synopsis
16
17#include <initializer_list>
18
19namespace std
20{
21
22namespace regex_constants
23{
24
25emum syntax_option_type
26{
27 icase = unspecified,
28 nosubs = unspecified,
29 optimize = unspecified,
30 collate = unspecified,
31 ECMAScript = unspecified,
32 basic = unspecified,
33 extended = unspecified,
34 awk = unspecified,
35 grep = unspecified,
36 egrep = unspecified
37};
38
39constexpr syntax_option_type operator~(syntax_option_type f);
40constexpr syntax_option_type operator&(syntax_option_type lhs, syntax_option_type rhs);
41constexpr syntax_option_type operator|(syntax_option_type lhs, syntax_option_type rhs);
42
43enum match_flag_type
44{
45 match_default = 0,
46 match_not_bol = unspecified,
47 match_not_eol = unspecified,
48 match_not_bow = unspecified,
49 match_not_eow = unspecified,
50 match_any = unspecified,
51 match_not_null = unspecified,
52 match_continuous = unspecified,
53 match_prev_avail = unspecified,
54 format_default = 0,
55 format_sed = unspecified,
56 format_no_copy = unspecified,
57 format_first_only = unspecified
58};
59
60constexpr match_flag_type operator~(match_flag_type f);
61constexpr match_flag_type operator&(match_flag_type lhs, match_flag_type rhs);
62constexpr match_flag_type operator|(match_flag_type lhs, match_flag_type rhs);
63
64enum error_type
65{
66 error_collate = unspecified,
67 error_ctype = unspecified,
68 error_escape = unspecified,
69 error_backref = unspecified,
70 error_brack = unspecified,
71 error_paren = unspecified,
72 error_brace = unspecified,
73 error_badbrace = unspecified,
74 error_range = unspecified,
75 error_space = unspecified,
76 error_badrepeat = unspecified,
77 error_complexity = unspecified,
78 error_stack = unspecified
79};
80
81} // regex_constants
82
83class regex_error
84 : public runtime_error
85{
86public:
87 explicit regex_error(regex_constants::error_type ecode);
88 regex_constants::error_type code() const;
89};
90
91template <class charT>
92struct regex_traits
93{
94public:
95 typedef charT char_type;
96 typedef basic_string<char_type> string_type;
97 typedef locale locale_type;
98 typedef /bitmask_type/ char_class_type;
99
100 regex_traits();
101
102 static size_t length(const char_type* p);
103 charT translate(charT c) const;
104 charT translate_nocase(charT c) const;
105 template <class ForwardIterator>
106 string_type
107 transform(ForwardIterator first, ForwardIterator last) const;
108 template <class ForwardIterator>
109 string_type
110 transform_primary( ForwardIterator first, ForwardIterator last) const;
111 template <class ForwardIterator>
112 string_type
113 lookup_collatename(ForwardIterator first, ForwardIterator last) const;
114 template <class ForwardIterator>
115 char_class_type
116 lookup_classname(ForwardIterator first, ForwardIterator last,
117 bool icase = false) const;
118 bool isctype(charT c, char_class_type f) const;
119 int value(charT ch, int radix) const;
120 locale_type imbue(locale_type l);
121 locale_type getloc()const;
122};
123
124template <class charT, class traits = regex_traits<charT>>
125class basic_regex
126{
127public:
128 // types:
129 typedef charT value_type;
130 typedef regex_constants::syntax_option_type flag_type;
131 typedef typename traits::locale_type locale_type;
132
133 // constants:
134 static constexpr regex_constants::syntax_option_type icase = regex_constants::icase;
135 static constexpr regex_constants::syntax_option_type nosubs = regex_constants::nosubs;
136 static constexpr regex_constants::syntax_option_type optimize = regex_constants::optimize;
137 static constexpr regex_constants::syntax_option_type collate = regex_constants::collate;
138 static constexpr regex_constants::syntax_option_type ECMAScript = regex_constants::ECMAScript;
139 static constexpr regex_constants::syntax_option_type basic = regex_constants::basic;
140 static constexpr regex_constants::syntax_option_type extended = regex_constants::extended;
141 static constexpr regex_constants::syntax_option_type awk = regex_constants::awk;
142 static constexpr regex_constants::syntax_option_type grep = regex_constants::grep;
143 static constexpr regex_constants::syntax_option_type egrep = regex_constants::egrep;
144
145 // construct/copy/destroy:
146 basic_regex();
147 explicit basic_regex(const charT* p, flag_type f = regex_constants::ECMAScript);
148 basic_regex(const charT* p, size_t len, flag_type f);
149 basic_regex(const basic_regex&);
150 basic_regex(basic_regex&&);
151 template <class ST, class SA>
152 explicit basic_regex(const basic_string<charT, ST, SA>& p,
153 flag_type f = regex_constants::ECMAScript);
154 template <class ForwardIterator>
155 basic_regex(ForwardIterator first, ForwardIterator last,
156 flag_type f = regex_constants::ECMAScript);
157 basic_regex(initializer_list<charT>, flag_type = regex_constants::ECMAScript);
158
159 ~basic_regex();
160
161 basic_regex& operator=(const basic_regex&);
162 basic_regex& operator=(basic_regex&&);
163 basic_regex& operator=(const charT* ptr);
164 basic_regex& operator=(initializer_list<charT> il);
165 template <class ST, class SA>
166 basic_regex& operator=(const basic_string<charT, ST, SA>& p);
167
168 // assign:
169 basic_regex& assign(const basic_regex& that);
170 basic_regex& assign(basic_regex&& that);
171 basic_regex& assign(const charT* ptr, flag_type f = regex_constants::ECMAScript);
172 basic_regex& assign(const charT* p, size_t len, flag_type f);
173 template <class string_traits, class A>
174 basic_regex& assign(const basic_string<charT, string_traits, A>& s,
175 flag_type f = regex_constants::ECMAScript);
176 template <class InputIterator>
177 basic_regex& assign(InputIterator first, InputIterator last,
178 flag_type f = regex_constants::ECMAScript);
179 basic_regex& assign(initializer_list<charT>, flag_type = regex_constants::ECMAScript);
180
181 // const operations:
182 unsigned mark_count() const;
183 flag_type flags() const;
184
185 // locale:
186 locale_type imbue(locale_type loc);
187 locale_type getloc() const;
188
189 // swap:
190 void swap(basic_regex&);
191};
192
193typedef basic_regex<char> regex;
194typedef basic_regex<wchar_t> wregex;
195
196template <class charT, class traits>
197 void swap(basic_regex<charT, traits>& e1, basic_regex<charT, traits>& e2);
198
199template <class BidirectionalIterator>
200class sub_match
201 : public pair<BidirectionalIterator, BidirectionalIterator>
202{
203public:
204 typedef typename iterator_traits<BidirectionalIterator>::value_type value_type;
205 typedef typename iterator_traits<BidirectionalIterator>::difference_type difference_type;
206 typedef BidirectionalIterator iterator;
207 typedef basic_string<value_type> string_type;
208
209 bool matched;
210
211 difference_type length() const;
212 operator string_type() const;
213 string_type str() const;
214
215 int compare(const sub_match& s) const;
216 int compare(const string_type& s) const;
217 int compare(const value_type* s) const;
218};
219
220typedef sub_match<const char*> csub_match;
221typedef sub_match<const wchar_t*> wcsub_match;
222typedef sub_match<string::const_iterator> ssub_match;
223typedef sub_match<wstring::const_iterator> wssub_match;
224
225template <class BiIter>
226 bool
227 operator==(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
228
229template <class BiIter>
230 bool
231 operator!=(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
232
233template <class BiIter>
234 bool
235 operator<(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
236
237template <class BiIter>
238 bool
239 operator<=(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
240
241template <class BiIter>
242 bool
243 operator>=(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
244
245template <class BiIter>
246 bool
247 operator>(const sub_match<BiIter>& lhs, const sub_match<BiIter>& rhs);
248
249template <class BiIter, class ST, class SA>
250 bool
251 operator==(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
252 const sub_match<BiIter>& rhs);
253
254template <class BiIter, class ST, class SA>
255 bool
256 operator!=(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
257 const sub_match<BiIter>& rhs);
258
259template <class BiIter, class ST, class SA>
260 bool
261 operator<(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
262 const sub_match<BiIter>& rhs);
263
264template <class BiIter, class ST, class SA>
265 bool
266 operator>(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
267 const sub_match<BiIter>& rhs);
268
269template <class BiIter, class ST, class SA>
270 bool operator>=(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
271 const sub_match<BiIter>& rhs);
272
273template <class BiIter, class ST, class SA>
274 bool
275 operator<=(const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& lhs,
276 const sub_match<BiIter>& rhs);
277
278template <class BiIter, class ST, class SA>
279 bool
280 operator==(const sub_match<BiIter>& lhs,
281 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
282
283template <class BiIter, class ST, class SA>
284 bool
285 operator!=(const sub_match<BiIter>& lhs,
286 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
287
288template <class BiIter, class ST, class SA>
289 bool
290 operator<(const sub_match<BiIter>& lhs,
291 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
292
293template <class BiIter, class ST, class SA>
294 bool operator>(const sub_match<BiIter>& lhs,
295 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
296
297template <class BiIter, class ST, class SA>
298 bool
299 operator>=(const sub_match<BiIter>& lhs,
300 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
301
302template <class BiIter, class ST, class SA>
303 bool
304 operator<=(const sub_match<BiIter>& lhs,
305 const basic_string<typename iterator_traits<BiIter>::value_type, ST, SA>& rhs);
306
307template <class BiIter>
308 bool
309 operator==(typename iterator_traits<BiIter>::value_type const* lhs,
310 const sub_match<BiIter>& rhs);
311
312template <class BiIter>
313 bool
314 operator!=(typename iterator_traits<BiIter>::value_type const* lhs,
315 const sub_match<BiIter>& rhs);
316
317template <class BiIter>
318 bool
319 operator<(typename iterator_traits<BiIter>::value_type const* lhs,
320 const sub_match<BiIter>& rhs);
321
322template <class BiIter>
323 bool
324 operator>(typename iterator_traits<BiIter>::value_type const* lhs,
325 const sub_match<BiIter>& rhs);
326
327template <class BiIter>
328 bool
329 operator>=(typename iterator_traits<BiIter>::value_type const* lhs,
330 const sub_match<BiIter>& rhs);
331
332template <class BiIter>
333 bool
334 operator<=(typename iterator_traits<BiIter>::value_type const* lhs,
335 const sub_match<BiIter>& rhs);
336
337template <class BiIter>
338 bool
339 operator==(const sub_match<BiIter>& lhs,
340 typename iterator_traits<BiIter>::value_type const* rhs);
341
342template <class BiIter>
343 bool
344 operator!=(const sub_match<BiIter>& lhs,
345 typename iterator_traits<BiIter>::value_type const* rhs);
346
347template <class BiIter>
348 bool
349 operator<(const sub_match<BiIter>& lhs,
350 typename iterator_traits<BiIter>::value_type const* rhs);
351
352template <class BiIter>
353 bool
354 operator>(const sub_match<BiIter>& lhs,
355 typename iterator_traits<BiIter>::value_type const* rhs);
356
357template <class BiIter>
358 bool
359 operator>=(const sub_match<BiIter>& lhs,
360 typename iterator_traits<BiIter>::value_type const* rhs);
361
362template <class BiIter>
363 bool
364 operator<=(const sub_match<BiIter>& lhs,
365 typename iterator_traits<BiIter>::value_type const* rhs);
366
367template <class BiIter>
368 bool
369 operator==(typename iterator_traits<BiIter>::value_type const& lhs,
370 const sub_match<BiIter>& rhs);
371
372template <class BiIter>
373 bool
374 operator!=(typename iterator_traits<BiIter>::value_type const& lhs,
375 const sub_match<BiIter>& rhs);
376
377template <class BiIter>
378 bool
379 operator<(typename iterator_traits<BiIter>::value_type const& lhs,
380 const sub_match<BiIter>& rhs);
381
382template <class BiIter>
383 bool
384 operator>(typename iterator_traits<BiIter>::value_type const& lhs,
385 const sub_match<BiIter>& rhs);
386
387template <class BiIter>
388 bool
389 operator>=(typename iterator_traits<BiIter>::value_type const& lhs,
390 const sub_match<BiIter>& rhs);
391
392template <class BiIter>
393 bool
394 operator<=(typename iterator_traits<BiIter>::value_type const& lhs,
395 const sub_match<BiIter>& rhs);
396
397template <class BiIter>
398 bool
399 operator==(const sub_match<BiIter>& lhs,
400 typename iterator_traits<BiIter>::value_type const& rhs);
401
402template <class BiIter>
403 bool
404 operator!=(const sub_match<BiIter>& lhs,
405 typename iterator_traits<BiIter>::value_type const& rhs);
406
407template <class BiIter>
408 bool
409 operator<(const sub_match<BiIter>& lhs,
410 typename iterator_traits<BiIter>::value_type const& rhs);
411
412template <class BiIter>
413 bool
414 operator>(const sub_match<BiIter>& lhs,
415 typename iterator_traits<BiIter>::value_type const& rhs);
416
417template <class BiIter>
418 bool
419 operator>=(const sub_match<BiIter>& lhs,
420 typename iterator_traits<BiIter>::value_type const& rhs);
421
422template <class BiIter>
423 bool
424 operator<=(const sub_match<BiIter>& lhs,
425 typename iterator_traits<BiIter>::value_type const& rhs);
426
427template <class charT, class ST, class BiIter>
428 basic_ostream<charT, ST>&
429 operator<<(basic_ostream<charT, ST>& os, const sub_match<BiIter>& m);
430
431template <class BidirectionalIterator,
432 class Allocator = allocator<sub_match<BidirectionalIterator>>>
433class match_results
434{
435public:
436 typedef sub_match<BidirectionalIterator> value_type;
437 typedef const value_type& const_reference;
438 typedef const_reference reference;
439 typedef /implementation-defined/ const_iterator;
440 typedef const_iterator iterator;
441 typedef typename iterator_traits<BidirectionalIterator>::difference_type difference_type;
442 typedef typename allocator_traits<Allocator>::size_type size_type;
443 typedef Allocator allocator_type;
444 typedef typename iterator_traits<BidirectionalIterator>::value_type char_type;
445 typedef basic_string<char_type> string_type;
446
447 // construct/copy/destroy:
448 explicit match_results(const Allocator& a = Allocator());
449 match_results(const match_results& m);
450 match_results(match_results&& m);
451 match_results& operator=(const match_results& m);
452 match_results& operator=(match_results&& m);
453 ~match_results();
454
455 // size:
456 size_type size() const;
457 size_type max_size() const;
458 bool empty() const;
459
460 // element access:
461 difference_type length(size_type sub = 0) const;
462 difference_type position(size_type sub = 0) const;
463 string_type str(size_type sub = 0) const;
464 const_reference operator[](size_type n) const;
465
466 const_reference prefix() const;
467 const_reference suffix() const;
468
469 const_iterator begin() const;
470 const_iterator end() const;
471 const_iterator cbegin() const;
472 const_iterator cend() const;
473
474 // format:
475 template <class OutputIter>
476 OutputIter
477 format(OutputIter out, const char_type* fmt_first,
478 const char_type* fmt_last,
479 regex_constants::match_flag_type flags = regex_constants::format_default) const;
480 template <class OutputIter, class ST, class SA>
481 OutputIter
482 format(OutputIter out, const basic_string<char_type, ST, SA>& fmt,
483 regex_constants::match_flag_type flags = regex_constants::format_default) const;
484 template <class ST, class SA>
485 basic_string<char_type, ST, SA>
486 format(const basic_string<char_type, ST, SA>& fmt,
487 regex_constants::match_flag_type flags = regex_constants::format_default) const;
488 string_type
489 format(const char_type* fmt,
490 regex_constants::match_flag_type flags = regex_constants::format_default) const;
491
492 // allocator:
493 allocator_type get_allocator() const;
494
495 // swap:
496 void swap(match_results& that);
497};
498
499typedef match_results<const char*> cmatch;
500typedef match_results<const wchar_t*> wcmatch;
501typedef match_results<string::const_iterator> smatch;
502typedef match_results<wstring::const_iterator> wsmatch;
503
504template <class BidirectionalIterator, class Allocator>
505 bool
506 operator==(const match_results<BidirectionalIterator, Allocator>& m1,
507 const match_results<BidirectionalIterator, Allocator>& m2);
508
509template <class BidirectionalIterator, class Allocator>
510 bool
511 operator!=(const match_results<BidirectionalIterator, Allocator>& m1,
512 const match_results<BidirectionalIterator, Allocator>& m2);
513
514template <class BidirectionalIterator, class Allocator>
515 void
516 swap(match_results<BidirectionalIterator, Allocator>& m1,
517 match_results<BidirectionalIterator, Allocator>& m2);
518
519template <class BidirectionalIterator, class Allocator, class charT, class traits>
520 bool
521 regex_match(BidirectionalIterator first, BidirectionalIterator last,
522 match_results<BidirectionalIterator, Allocator>& m,
523 const basic_regex<charT, traits>& e,
524 regex_constants::match_flag_type flags = regex_constants::match_default);
525
526template <class BidirectionalIterator, class charT, class traits>
527 bool
528 regex_match(BidirectionalIterator first, BidirectionalIterator last,
529 const basic_regex<charT, traits>& e,
530 regex_constants::match_flag_type flags = regex_constants::match_default);
531
532template <class charT, class Allocator, class traits>
533 bool
534 regex_match(const charT* str, match_results<const charT*, Allocator>& m,
535 const basic_regex<charT, traits>& e,
536 regex_constants::match_flag_type flags = regex_constants::match_default);
537
538template <class ST, class SA, class Allocator, class charT, class traits>
539 bool
540 regex_match(const basic_string<charT, ST, SA>& s,
541 match_results<typename basic_string<charT, ST, SA>::const_iterator, Allocator>& m,
542 const basic_regex<charT, traits>& e,
543 regex_constants::match_flag_type flags = regex_constants::match_default);
544
545template <class charT, class traits>
546 bool
547 regex_match(const charT* str, const basic_regex<charT, traits>& e,
548 regex_constants::match_flag_type flags = regex_constants::match_default);
549
550template <class ST, class SA, class charT, class traits>
551 bool
552 regex_match(const basic_string<charT, ST, SA>& s,
553 const basic_regex<charT, traits>& e,
554 regex_constants::match_flag_type flags = regex_constants::match_default);
555
556template <class BidirectionalIterator, class Allocator, class charT, class traits>
557 bool
558 regex_search(BidirectionalIterator first, BidirectionalIterator last,
559 match_results<BidirectionalIterator, Allocator>& m,
560 const basic_regex<charT, traits>& e,
561 regex_constants::match_flag_type flags = regex_constants::match_default);
562
563template <class BidirectionalIterator, class charT, class traits>
564 bool
565 regex_search(BidirectionalIterator first, BidirectionalIterator last,
566 const basic_regex<charT, traits>& e,
567 regex_constants::match_flag_type flags = regex_constants::match_default);
568
569template <class charT, class Allocator, class traits>
570 bool
571 regex_search(const charT* str, match_results<const charT*, Allocator>& m,
572 const basic_regex<charT, traits>& e,
573 regex_constants::match_flag_type flags = regex_constants::match_default);
574
575template <class charT, class traits>
576 bool
577 regex_search(const charT* str, const basic_regex<charT, traits>& e,
578 regex_constants::match_flag_type flags = regex_constants::match_default);
579
580template <class ST, class SA, class charT, class traits>
581 bool
582 regex_search(const basic_string<charT, ST, SA>& s,
583 const basic_regex<charT, traits>& e,
584 regex_constants::match_flag_type flags = regex_constants::match_default);
585
586template <class ST, class SA, class Allocator, class charT, class traits>
587 bool
588 regex_search(const basic_string<charT, ST, SA>& s,
589 match_results<typename basic_string<charT, ST, SA>::const_iterator, Allocator>& m,
590 const basic_regex<charT, traits>& e,
591 regex_constants::match_flag_type flags = regex_constants::match_default);
592
593template <class OutputIterator, class BidirectionalIterator,
594 class traits, class charT, class ST, class SA>
595 OutputIterator
596 regex_replace(OutputIterator out,
597 BidirectionalIterator first, BidirectionalIterator last,
598 const basic_regex<charT, traits>& e,
599 const basic_string<charT, ST, SA>& fmt,
600 regex_constants::match_flag_type flags = regex_constants::match_default);
601
602template <class OutputIterator, class BidirectionalIterator,
603 class traits, class charT>
604 OutputIterator
605 regex_replace(OutputIterator out,
606 BidirectionalIterator first, BidirectionalIterator last,
607 const basic_regex<charT, traits>& e, const charT* fmt,
608 regex_constants::match_flag_type flags = regex_constants::match_default);
609
610template <class traits, class charT, class ST, class SA, class FST, class FSA>>
611 basic_string<charT, ST, SA>
612 regex_replace(const basic_string<charT, ST, SA>& s,
613 const basic_regex<charT, traits>& e,
614 const basic_string<charT, FST, FSA>& fmt,
615 regex_constants::match_flag_type flags = regex_constants::match_default);
616
617template <class traits, class charT, class ST, class SA>
618 basic_string<charT, ST, SA>
619 regex_replace(const basic_string<charT, ST, SA>& s,
620 const basic_regex<charT, traits>& e, const charT* fmt,
621 regex_constants::match_flag_type flags = regex_constants::match_default);
622
623template <class traits, class charT, class ST, class SA>
624 basic_string<charT>
625 regex_replace(const charT* s,
626 const basic_regex<charT, traits>& e,
627 const basic_string<charT, ST, SA>& fmt,
628 regex_constants::match_flag_type flags = regex_constants::match_default);
629
630template <class traits, class charT>
631 basic_string<charT>
632 regex_replace(const charT* s,
633 const basic_regex<charT, traits>& e,
634 const charT* fmt,
635 regex_constants::match_flag_type flags = regex_constants::match_default);
636
637template <class BidirectionalIterator,
638 class charT = typename iterator_traits< BidirectionalIterator>::value_type,
639 class traits = regex_traits<charT>>
640class regex_iterator
641{
642public:
643 typedef basic_regex<charT, traits> regex_type;
644 typedef match_results<BidirectionalIterator> value_type;
645 typedef ptrdiff_t difference_type;
646 typedef const value_type* pointer;
647 typedef const value_type& reference;
648 typedef forward_iterator_tag iterator_category;
649
650 regex_iterator();
651 regex_iterator(BidirectionalIterator a, BidirectionalIterator b,
652 const regex_type& re,
653 regex_constants::match_flag_type m = regex_constants::match_default);
654 regex_iterator(const regex_iterator&);
655 regex_iterator& operator=(const regex_iterator&);
656
657 bool operator==(const regex_iterator&) const;
658 bool operator!=(const regex_iterator&) const;
659
660 const value_type& operator*() const;
661 const value_type* operator->() const;
662
663 regex_iterator& operator++();
664 regex_iterator operator++(int);
665};
666
667typedef regex_iterator<const char*> cregex_iterator;
668typedef regex_iterator<const wchar_t*> wcregex_iterator;
669typedef regex_iterator<string::const_iterator> sregex_iterator;
670typedef regex_iterator<wstring::const_iterator> wsregex_iterator;
671
672template <class BidirectionalIterator,
673 class charT = typename iterator_traits< BidirectionalIterator>::value_type,
674 class traits = regex_traits<charT>>
675class regex_token_iterator
676{
677public:
678 typedef basic_regex<charT, traits> regex_type;
679 typedef sub_match<BidirectionalIterator> value_type;
680 typedef ptrdiff_t difference_type;
681 typedef const value_type* pointer;
682 typedef const value_type& reference;
683 typedef forward_iterator_tag iterator_category;
684
685 regex_token_iterator();
686 regex_token_iterator(BidirectionalIterator a, BidirectionalIterator b,
687 const regex_type& re, int submatch = 0,
688 regex_constants::match_flag_type m = regex_constants::match_default);
689 regex_token_iterator(BidirectionalIterator a, BidirectionalIterator b,
690 const regex_type& re, const vector<int>& submatches,
691 regex_constants::match_flag_type m = regex_constants::match_default);
692 regex_token_iterator(BidirectionalIterator a, BidirectionalIterator b,
693 const regex_type& re, initializer_list<int> submatches,
694 regex_constants::match_flag_type m = regex_constants::match_default);
695 template <size_t N>
696 regex_token_iterator(BidirectionalIterator a, BidirectionalIterator b,
697 const regex_type& re, const int (&submatches)[N],
698 regex_constants::match_flag_type m = regex_constants::match_default);
699 regex_token_iterator(const regex_token_iterator&);
700 regex_token_iterator& operator=(const regex_token_iterator&);
701
702 bool operator==(const regex_token_iterator&) const;
703 bool operator!=(const regex_token_iterator&) const;
704
705 const value_type& operator*() const;
706 const value_type* operator->() const;
707
708 regex_token_iterator& operator++();
709 regex_token_iterator operator++(int);
710};
711
712typedef regex_token_iterator<const char*> cregex_token_iterator;
713typedef regex_token_iterator<const wchar_t*> wcregex_token_iterator;
714typedef regex_token_iterator<string::const_iterator> sregex_token_iterator;
715typedef regex_token_iterator<wstring::const_iterator> wsregex_token_iterator;
716
717} // std
718*/
719
720#include <__config>
721#include <stdexcept>
722#include <__locale>
Howard Hinnant8c2c18d2010-06-24 21:28:00 +0000723#include <initializer_list>
Howard Hinnantcd85b9e2010-06-29 18:37:43 +0000724#include <utility>
725#include <iterator>
726#include <string>
Howard Hinnant7e9d84b2010-06-30 00:21:42 +0000727#include <memory>
728#include <vector>
Howard Hinnant3257c982010-06-17 00:34:59 +0000729
730#pragma GCC system_header
731
732_LIBCPP_BEGIN_NAMESPACE_STD
733
734namespace regex_constants
735{
736
737// syntax_option_type
738
739enum syntax_option_type
740{
741 icase = 1 << 0,
742 nosubs = 1 << 1,
743 optimize = 1 << 2,
744 collate = 1 << 3,
745 ECMAScript = 1 << 4,
746 basic = 1 << 5,
747 extended = 1 << 6,
748 awk = 1 << 7,
749 grep = 1 << 8,
750 egrep = 1 << 9
751};
752
753inline
754/*constexpr*/
755syntax_option_type
756operator~(syntax_option_type __x)
757{
758 return syntax_option_type(~int(__x));
759}
760
761inline
762/*constexpr*/
763syntax_option_type
764operator&(syntax_option_type __x, syntax_option_type __y)
765{
766 return syntax_option_type(int(__x) & int(__y));
767}
768
769inline
770/*constexpr*/
771syntax_option_type
772operator|(syntax_option_type __x, syntax_option_type __y)
773{
774 return syntax_option_type(int(__x) | int(__y));
775}
776
777inline
778/*constexpr*/
779syntax_option_type
780operator^(syntax_option_type __x, syntax_option_type __y)
781{
782 return syntax_option_type(int(__x) ^ int(__y));
783}
784
785inline
786/*constexpr*/
787syntax_option_type&
788operator&=(syntax_option_type& __x, syntax_option_type __y)
789{
790 __x = __x & __y;
791 return __x;
792}
793
794inline
795/*constexpr*/
796syntax_option_type&
797operator|=(syntax_option_type& __x, syntax_option_type __y)
798{
799 __x = __x | __y;
800 return __x;
801}
802
803inline
804/*constexpr*/
805syntax_option_type&
806operator^=(syntax_option_type& __x, syntax_option_type __y)
807{
808 __x = __x ^ __y;
809 return __x;
810}
811
812// match_flag_type
813
814enum match_flag_type
815{
816 match_default = 0,
817 match_not_bol = 1 << 0,
818 match_not_eol = 1 << 1,
819 match_not_bow = 1 << 2,
820 match_not_eow = 1 << 3,
821 match_any = 1 << 4,
822 match_not_null = 1 << 5,
823 match_continuous = 1 << 6,
824 match_prev_avail = 1 << 7,
825 format_default = 0,
826 format_sed = 1 << 8,
827 format_no_copy = 1 << 9,
828 format_first_only = 1 << 10
829};
830
831inline
832/*constexpr*/
833match_flag_type
834operator~(match_flag_type __x)
835{
836 return match_flag_type(~int(__x));
837}
838
839inline
840/*constexpr*/
841match_flag_type
842operator&(match_flag_type __x, match_flag_type __y)
843{
844 return match_flag_type(int(__x) & int(__y));
845}
846
847inline
848/*constexpr*/
849match_flag_type
850operator|(match_flag_type __x, match_flag_type __y)
851{
852 return match_flag_type(int(__x) | int(__y));
853}
854
855inline
856/*constexpr*/
857match_flag_type
858operator^(match_flag_type __x, match_flag_type __y)
859{
860 return match_flag_type(int(__x) ^ int(__y));
861}
862
863inline
864/*constexpr*/
865match_flag_type&
866operator&=(match_flag_type& __x, match_flag_type __y)
867{
868 __x = __x & __y;
869 return __x;
870}
871
872inline
873/*constexpr*/
874match_flag_type&
875operator|=(match_flag_type& __x, match_flag_type __y)
876{
877 __x = __x | __y;
878 return __x;
879}
880
881inline
882/*constexpr*/
883match_flag_type&
884operator^=(match_flag_type& __x, match_flag_type __y)
885{
886 __x = __x ^ __y;
887 return __x;
888}
889
890enum error_type
891{
892 error_collate = 1,
893 error_ctype,
894 error_escape,
895 error_backref,
896 error_brack,
897 error_paren,
898 error_brace,
899 error_badbrace,
900 error_range,
901 error_space,
902 error_badrepeat,
903 error_complexity,
Howard Hinnant8c2c18d2010-06-24 21:28:00 +0000904 error_stack,
905 error_temp
Howard Hinnant3257c982010-06-17 00:34:59 +0000906};
907
908} // regex_constants
909
910class _LIBCPP_EXCEPTION_ABI regex_error
911 : public runtime_error
912{
913 regex_constants::error_type __code_;
914public:
915 explicit regex_error(regex_constants::error_type __ecode);
916 virtual ~regex_error() throw();
917 regex_constants::error_type code() const {return __code_;}
918};
919
920template <class _CharT>
921struct regex_traits
922{
923public:
924 typedef _CharT char_type;
925 typedef basic_string<char_type> string_type;
926 typedef locale locale_type;
Howard Hinnantf409d2f2010-06-21 21:01:43 +0000927 typedef ctype_base::mask char_class_type;
Howard Hinnant3257c982010-06-17 00:34:59 +0000928
Howard Hinnantf409d2f2010-06-21 21:01:43 +0000929 static const char_class_type __regex_word = 0x80;
Howard Hinnant3257c982010-06-17 00:34:59 +0000930private:
931 locale __loc_;
932 const ctype<char_type>* __ct_;
933 const collate<char_type>* __col_;
934
935public:
936 regex_traits();
937
938 static size_t length(const char_type* __p)
939 {return char_traits<char_type>::length(__p);}
940 char_type translate(char_type __c) const {return __c;}
941 char_type translate_nocase(char_type __c) const;
942 template <class _ForwardIterator>
943 string_type
944 transform(_ForwardIterator __f, _ForwardIterator __l) const;
945 template <class _ForwardIterator>
946 string_type
947 transform_primary( _ForwardIterator __f, _ForwardIterator __l) const
948 {return __transform_primary(__f, __l, char_type());}
949 template <class _ForwardIterator>
950 string_type
951 lookup_collatename(_ForwardIterator __f, _ForwardIterator __l) const
952 {return __lookup_collatename(__f, __l, char_type());}
953 template <class _ForwardIterator>
954 char_class_type
955 lookup_classname(_ForwardIterator __f, _ForwardIterator __l,
Howard Hinnantf409d2f2010-06-21 21:01:43 +0000956 bool __icase = false) const
957 {return __lookup_classname(__f, __l, __icase, char_type());}
958 bool isctype(char_type __c, char_class_type __m) const;
959 int value(char_type __ch, int __radix) const
960 {return __value(__ch, __radix);}
Howard Hinnant3257c982010-06-17 00:34:59 +0000961 locale_type imbue(locale_type __l);
962 locale_type getloc()const {return __loc_;}
963
964private:
965 void __init();
966
967 template <class _ForwardIterator>
968 string_type
969 __transform_primary(_ForwardIterator __f, _ForwardIterator __l, char) const;
970 template <class _ForwardIterator>
971 string_type
972 __transform_primary(_ForwardIterator __f, _ForwardIterator __l, wchar_t) const;
973
974 template <class _ForwardIterator>
975 string_type
976 __lookup_collatename(_ForwardIterator __f, _ForwardIterator __l, char) const;
977 template <class _ForwardIterator>
978 string_type
979 __lookup_collatename(_ForwardIterator __f, _ForwardIterator __l, wchar_t) const;
Howard Hinnantf409d2f2010-06-21 21:01:43 +0000980
981 template <class _ForwardIterator>
982 char_class_type
983 __lookup_classname(_ForwardIterator __f, _ForwardIterator __l,
984 bool __icase, char) const;
985 template <class _ForwardIterator>
986 char_class_type
987 __lookup_classname(_ForwardIterator __f, _ForwardIterator __l,
988 bool __icase, wchar_t) const;
989
990 static int __value(unsigned char __ch, int __radix);
991 int __value(char __ch, int __radix) const
992 {return __value(static_cast<unsigned char>(__ch), __radix);}
993 int __value(wchar_t __ch, int __radix) const;
Howard Hinnant3257c982010-06-17 00:34:59 +0000994};
995
996template <class _CharT>
997regex_traits<_CharT>::regex_traits()
998{
999 __init();
1000}
1001
1002template <class _CharT>
1003typename regex_traits<_CharT>::char_type
1004regex_traits<_CharT>::translate_nocase(char_type __c) const
1005{
1006 return __ct_->tolower(__c);
1007}
1008
1009template <class _CharT>
1010template <class _ForwardIterator>
1011typename regex_traits<_CharT>::string_type
1012regex_traits<_CharT>::transform(_ForwardIterator __f, _ForwardIterator __l) const
1013{
1014 string_type __s(__f, __l);
1015 return __col_->transform(__s.data(), __s.data() + __s.size());
1016}
1017
1018template <class _CharT>
1019void
1020regex_traits<_CharT>::__init()
1021{
1022 __ct_ = &use_facet<ctype<char_type> >(__loc_);
1023 __col_ = &use_facet<collate<char_type> >(__loc_);
1024}
1025
1026template <class _CharT>
1027typename regex_traits<_CharT>::locale_type
1028regex_traits<_CharT>::imbue(locale_type __l)
1029{
1030 locale __r = __loc_;
1031 __loc_ = __l;
1032 __init();
1033 return __r;
1034}
1035
1036// transform_primary is very FreeBSD-specific
1037
1038template <class _CharT>
1039template <class _ForwardIterator>
1040typename regex_traits<_CharT>::string_type
1041regex_traits<_CharT>::__transform_primary(_ForwardIterator __f,
1042 _ForwardIterator __l, char) const
1043{
1044 const string_type __s(__f, __l);
1045 string_type __d = __col_->transform(__s.data(), __s.data() + __s.size());
1046 switch (__d.size())
1047 {
1048 case 1:
1049 break;
1050 case 12:
1051 __d[11] = __d[3];
1052 break;
1053 default:
1054 __d.clear();
1055 break;
1056 }
1057 return __d;
1058}
1059
1060template <class _CharT>
1061template <class _ForwardIterator>
1062typename regex_traits<_CharT>::string_type
1063regex_traits<_CharT>::__transform_primary(_ForwardIterator __f,
1064 _ForwardIterator __l, wchar_t) const
1065{
1066 const string_type __s(__f, __l);
1067 string_type __d = __col_->transform(__s.data(), __s.data() + __s.size());
1068 switch (__d.size())
1069 {
1070 case 1:
1071 break;
1072 case 3:
1073 __d[2] = __d[0];
1074 break;
1075 default:
1076 __d.clear();
1077 break;
1078 }
1079 return __d;
1080}
1081
1082// lookup_collatename is very FreeBSD-specific
1083
Howard Hinnantf409d2f2010-06-21 21:01:43 +00001084string __get_collation_name(const char* __s);
Howard Hinnant3257c982010-06-17 00:34:59 +00001085
1086template <class _CharT>
1087template <class _ForwardIterator>
1088typename regex_traits<_CharT>::string_type
1089regex_traits<_CharT>::__lookup_collatename(_ForwardIterator __f,
1090 _ForwardIterator __l, char) const
1091{
1092 string_type __s(__f, __l);
1093 string_type __r;
1094 if (!__s.empty())
1095 {
1096 __r = __get_collation_name(__s.c_str());
1097 if (__r.empty() && __s.size() <= 2)
1098 {
1099 __r = __col_->transform(__s.data(), __s.data() + __s.size());
1100 if (__r.size() == 1 || __r.size() == 12)
1101 __r = __s;
1102 else
1103 __r.clear();
1104 }
1105 }
1106 return __r;
1107}
1108
1109template <class _CharT>
1110template <class _ForwardIterator>
1111typename regex_traits<_CharT>::string_type
1112regex_traits<_CharT>::__lookup_collatename(_ForwardIterator __f,
1113 _ForwardIterator __l, wchar_t) const
1114{
1115 string_type __s(__f, __l);
1116 string __n;
1117 __n.reserve(__s.size());
1118 for (typename string_type::const_iterator __i = __s.begin(), __e = __s.end();
1119 __i != __e; ++__i)
1120 {
1121 if (static_cast<unsigned>(*__i) >= 127)
1122 return string_type();
1123 __n.push_back(char(*__i));
1124 }
1125 string_type __r;
1126 if (!__s.empty())
1127 {
1128 __n = __get_collation_name(__n.c_str());
1129 if (!__n.empty())
1130 __r.assign(__n.begin(), __n.end());
1131 else if (__s.size() <= 2)
1132 {
1133 __r = __col_->transform(__s.data(), __s.data() + __s.size());
1134 if (__r.size() == 1 || __r.size() == 3)
1135 __r = __s;
1136 else
1137 __r.clear();
1138 }
1139 }
1140 return __r;
1141}
1142
Howard Hinnantf409d2f2010-06-21 21:01:43 +00001143// lookup_classname
1144
1145ctype_base::mask __get_classname(const char* __s, bool __icase);
1146
1147template <class _CharT>
1148template <class _ForwardIterator>
1149typename regex_traits<_CharT>::char_class_type
1150regex_traits<_CharT>::__lookup_classname(_ForwardIterator __f,
1151 _ForwardIterator __l,
1152 bool __icase, char) const
1153{
1154 string_type __s(__f, __l);
1155 __ct_->tolower(&__s[0], &__s[0] + __s.size());
1156 return __get_classname(__s.c_str(), __icase);
1157}
1158
1159template <class _CharT>
1160template <class _ForwardIterator>
1161typename regex_traits<_CharT>::char_class_type
1162regex_traits<_CharT>::__lookup_classname(_ForwardIterator __f,
1163 _ForwardIterator __l,
1164 bool __icase, wchar_t) const
1165{
1166 string_type __s(__f, __l);
1167 __ct_->tolower(&__s[0], &__s[0] + __s.size());
1168 string __n;
1169 __n.reserve(__s.size());
1170 for (typename string_type::const_iterator __i = __s.begin(), __e = __s.end();
1171 __i != __e; ++__i)
1172 {
1173 if (static_cast<unsigned>(*__i) >= 127)
1174 return char_class_type();
1175 __n.push_back(char(*__i));
1176 }
1177 return __get_classname(__n.c_str(), __icase);
1178}
1179
1180template <class _CharT>
1181bool
1182regex_traits<_CharT>::isctype(char_type __c, char_class_type __m) const
1183{
1184 if (__ct_->is(__m, __c))
1185 return true;
1186 return (__c == '_' && (__m & __regex_word));
1187}
1188
1189template <class _CharT>
1190int
1191regex_traits<_CharT>::__value(unsigned char __ch, int __radix)
1192{
1193 if ((__ch & 0xF8u) == 0x30) // '0' <= __ch && __ch <= '7'
1194 return __ch - '0';
1195 if (__radix != 8)
1196 {
1197 if ((__ch & 0xFEu) == 0x38) // '8' <= __ch && __ch <= '9'
1198 return __ch - '0';
1199 if (__radix == 16)
1200 {
1201 __ch |= 0x20; // tolower
1202 if ('a' <= __ch && __ch <= 'f')
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001203 return __ch - ('a' - 10);
Howard Hinnantf409d2f2010-06-21 21:01:43 +00001204 }
1205 }
1206 return -1;
1207}
1208
1209template <class _CharT>
1210inline
1211int
1212regex_traits<_CharT>::__value(wchar_t __ch, int __radix) const
1213{
1214 return __value(static_cast<unsigned char>(__ct_->narrow(__ch, char_type())), __radix);
1215}
1216
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001217template <class _CharT> class __transition;
1218
1219template <class _CharT>
1220class __state
1221{
1222 typedef __transition<_CharT> __transition;
1223 __transition* __t1_;
1224 __transition* __t2_;
1225 int __state_;
1226 enum
1227 {
1228 __1_not_tried = 0,
1229 __1_succeded = 1,
1230 __1_failed = 2,
1231 __2_not_tried = 0,
1232 __2_succeded = 4,
1233 __2_failed = 8
1234 };
1235
1236 __state(const __state&);
1237 __state& operator=(const __state&);
1238public:
1239 __state()
1240 : __t1_(), __t2_(), __state_() {}
1241 ~__state();
1242
1243 const __state* operator()(_CharT __c);
1244
1245 void __add_one(__transition* __t) {__t1_ = __t;}
1246};
1247
1248template <class _CharT>
1249__state<_CharT>::~__state()
1250{
1251 delete __t1_;
1252 delete __t2_;
1253}
1254
1255template <class _CharT>
1256const __state<_CharT>*
1257__state<_CharT>::operator()(_CharT __c)
1258{
1259 const __state* __r = nullptr;
1260 if ((__state_ & 3) == 0)
1261 {
1262 if (__t1_)
1263 {
1264 __r = (*__t1_)(__c);
1265 if (__r)
1266 __state_ |= __1_succeded;
1267 else
1268 __state_ |= __1_failed;
1269 }
1270 else
1271 __state_ |= __1_failed;
1272 }
1273 else if ((__state_ & 0xC) == 0)
1274 {
1275 if (__t2_)
1276 {
1277 __r = (*__t2_)(__c);
1278 if (__r)
1279 __state_ |= __2_succeded;
1280 else
1281 __state_ |= __2_failed;
1282 }
1283 else
1284 __state_ |= __2_failed;
1285 }
1286 return __r;
1287}
1288
1289template <class _CharT>
1290class __transition
1291{
1292 __transition(const __transition&);
1293 __transition& operator=(const __transition&);
1294
1295 typedef __state<_CharT> __state;
1296 typedef unique_ptr<__state, void(*)(__state*)> __sptr;
1297
1298 static void __delete_state(__state* __p) {delete __p;}
1299 static void __ignore_state(__state*) {}
1300
1301protected:
1302 __sptr __sptr_;
1303public:
1304 __transition(bool __owns, __state* __st)
1305 : __sptr_(__st, __owns ? &__delete_state : &__ignore_state) {}
1306 virtual ~__transition() {}
1307
1308 virtual const __state* operator()(_CharT) const {return __sptr_.get();}
1309};
1310
1311template <class _CharT>
1312class __match_char
1313 : public __transition<_CharT>
1314{
1315 typedef __transition<_CharT> base;
1316 _CharT __c_;
1317public:
1318 __match_char(_CharT __c, bool __owns, __state<_CharT>* __st)
1319 : base(__owns, __st), __c_(__c) {}
1320
1321 virtual const __state<_CharT>* operator()(_CharT __c) const
1322 {return __c == __c_ ? base::__sptr_.get() : nullptr;}
1323};
1324
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001325template <class _CharT, class _Traits = regex_traits<_CharT> >
1326class basic_regex
1327{
1328public:
1329 // types:
1330 typedef _CharT value_type;
1331 typedef regex_constants::syntax_option_type flag_type;
1332 typedef typename _Traits::locale_type locale_type;
1333
1334private:
1335 _Traits __traits_;
1336 flag_type __flags_;
1337 unsigned __marked_count_;
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001338 int __open_count_;
1339 shared_ptr<__state<_CharT> > __start_;
1340 __state<_CharT>* __end_;
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001341
1342public:
1343 // constants:
1344 static const/*expr*/ regex_constants::syntax_option_type icase = regex_constants::icase;
1345 static const/*expr*/ regex_constants::syntax_option_type nosubs = regex_constants::nosubs;
1346 static const/*expr*/ regex_constants::syntax_option_type optimize = regex_constants::optimize;
1347 static const/*expr*/ regex_constants::syntax_option_type collate = regex_constants::collate;
1348 static const/*expr*/ regex_constants::syntax_option_type ECMAScript = regex_constants::ECMAScript;
1349 static const/*expr*/ regex_constants::syntax_option_type basic = regex_constants::basic;
1350 static const/*expr*/ regex_constants::syntax_option_type extended = regex_constants::extended;
1351 static const/*expr*/ regex_constants::syntax_option_type awk = regex_constants::awk;
1352 static const/*expr*/ regex_constants::syntax_option_type grep = regex_constants::grep;
1353 static const/*expr*/ regex_constants::syntax_option_type egrep = regex_constants::egrep;
1354
1355 // construct/copy/destroy:
1356 basic_regex();
1357 explicit basic_regex(const value_type* __p, flag_type __f = regex_constants::ECMAScript)
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001358 : __flags_(__f), __marked_count_(0), __open_count_(0), __end_(0)
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001359 {__parse(__p, __p + __traits_.length(__p));}
1360 basic_regex(const value_type* __p, size_t __len, flag_type __f)
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001361 : __flags_(__f), __marked_count_(0), __open_count_(0), __end_(0)
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001362 {__parse(__p, __p + __len);}
1363 basic_regex(const basic_regex&);
1364#ifdef _LIBCPP_MOVE
1365 basic_regex(basic_regex&&);
1366#endif
1367 template <class _ST, class _SA>
1368 explicit basic_regex(const basic_string<value_type, _ST, _SA>& __p,
1369 flag_type __f = regex_constants::ECMAScript)
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001370 : __flags_(__f), __marked_count_(0), __open_count_(0), __end_(0)
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001371 {__parse(__p.begin(), __p.end());}
1372 template <class _ForwardIterator>
1373 basic_regex(_ForwardIterator __first, _ForwardIterator __last,
1374 flag_type __f = regex_constants::ECMAScript)
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001375 : __flags_(__f), __marked_count_(0), __open_count_(0), __end_(0)
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001376 {__parse(__first, __last);}
1377 basic_regex(initializer_list<value_type> __il,
1378 flag_type __f = regex_constants::ECMAScript)
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001379 : __flags_(__f), __marked_count_(0), __open_count_(0), __end_(0)
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001380 {__parse(__il.begin(), __il.end());}
1381
1382 ~basic_regex();
1383
1384 basic_regex& operator=(const basic_regex&);
1385#ifdef _LIBCPP_MOVE
1386 basic_regex& operator=(basic_regex&&);
1387#endif
1388 basic_regex& operator=(const value_type* __p);
1389 basic_regex& operator=(initializer_list<value_type> __il);
1390 template <class _ST, class _SA>
1391 basic_regex& operator=(const basic_string<value_type, _ST, _SA>& __p);
1392
1393 // assign:
1394 basic_regex& assign(const basic_regex& __that);
1395#ifdef _LIBCPP_MOVE
1396 basic_regex& assign(basic_regex&& __that);
1397#endif
1398 basic_regex& assign(const value_type* __p, flag_type __f = regex_constants::ECMAScript);
1399 basic_regex& assign(const value_type* __p, size_t __len, flag_type __f);
1400 template <class _ST, class _SA>
1401 basic_regex& assign(const basic_string<value_type, _ST, _SA>& __s,
1402 flag_type __f = regex_constants::ECMAScript);
1403 template <class _InputIterator>
1404 basic_regex& assign(_InputIterator __first, _InputIterator __last,
1405 flag_type __f = regex_constants::ECMAScript);
1406 basic_regex& assign(initializer_list<value_type> __il,
1407 flag_type = regex_constants::ECMAScript);
1408
1409 // const operations:
1410 unsigned mark_count() const {return __marked_count_;}
1411 flag_type flags() const {return __flags_;}
1412
1413 // locale:
1414 locale_type imbue(locale_type __loc) {return __traits_.imbue(__loc);}
1415 locale_type getloc() const {return __traits_.getloc();}
1416
1417 // swap:
1418 void swap(basic_regex&);
1419
1420private:
1421 template <class _ForwardIterator>
1422 void __parse(_ForwardIterator __first, _ForwardIterator __last);
1423 template <class _ForwardIterator>
1424 _ForwardIterator
1425 __parse_basic_reg_exp(_ForwardIterator __first, _ForwardIterator __last);
1426 template <class _ForwardIterator>
1427 _ForwardIterator
1428 __parse_RE_expression(_ForwardIterator __first, _ForwardIterator __last);
1429 template <class _ForwardIterator>
1430 _ForwardIterator
1431 __parse_simple_RE(_ForwardIterator __first, _ForwardIterator __last);
1432 template <class _ForwardIterator>
1433 _ForwardIterator
1434 __parse_nondupl_RE(_ForwardIterator __first, _ForwardIterator __last);
1435 template <class _ForwardIterator>
1436 _ForwardIterator
1437 __parse_one_char_or_coll_elem_RE(_ForwardIterator __first, _ForwardIterator __last);
1438 template <class _ForwardIterator>
1439 _ForwardIterator
1440 __parse_Back_open_paren(_ForwardIterator __first, _ForwardIterator __last);
1441 template <class _ForwardIterator>
1442 _ForwardIterator
1443 __parse_Back_close_paren(_ForwardIterator __first, _ForwardIterator __last);
1444 template <class _ForwardIterator>
1445 _ForwardIterator
1446 __parse_Back_open_brace(_ForwardIterator __first, _ForwardIterator __last);
1447 template <class _ForwardIterator>
1448 _ForwardIterator
1449 __parse_Back_close_brace(_ForwardIterator __first, _ForwardIterator __last);
1450 template <class _ForwardIterator>
1451 _ForwardIterator
1452 __parse_BACKREF(_ForwardIterator __first, _ForwardIterator __last);
1453 template <class _ForwardIterator>
1454 _ForwardIterator
1455 __parse_ORD_CHAR(_ForwardIterator __first, _ForwardIterator __last);
1456 template <class _ForwardIterator>
1457 _ForwardIterator
1458 __parse_QUOTED_CHAR(_ForwardIterator __first, _ForwardIterator __last);
1459 template <class _ForwardIterator>
1460 _ForwardIterator
1461 __parse_RE_dupl_symbol(_ForwardIterator __first, _ForwardIterator __last);
Howard Hinnant0de86b62010-06-25 20:56:08 +00001462 template <class _ForwardIterator>
1463 _ForwardIterator
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001464 __parse_ERE_dupl_symbol(_ForwardIterator __first, _ForwardIterator __last);
1465 template <class _ForwardIterator>
1466 _ForwardIterator
Howard Hinnant0de86b62010-06-25 20:56:08 +00001467 __parse_bracket_expression(_ForwardIterator __first, _ForwardIterator __last);
1468 template <class _ForwardIterator>
1469 _ForwardIterator
1470 __parse_follow_list(_ForwardIterator __first, _ForwardIterator __last);
1471 template <class _ForwardIterator>
1472 _ForwardIterator
1473 __parse_expression_term(_ForwardIterator __first, _ForwardIterator __last);
1474 template <class _ForwardIterator>
1475 _ForwardIterator
1476 __parse_equivalence_class(_ForwardIterator __first, _ForwardIterator __last);
1477 template <class _ForwardIterator>
1478 _ForwardIterator
1479 __parse_character_class(_ForwardIterator __first, _ForwardIterator __last);
1480 template <class _ForwardIterator>
1481 _ForwardIterator
1482 __parse_collating_symbol(_ForwardIterator __first, _ForwardIterator __last);
1483 template <class _ForwardIterator>
1484 _ForwardIterator
1485 __parse_DUP_COUNT(_ForwardIterator __first, _ForwardIterator __last, int& __c);
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001486 template <class _ForwardIterator>
1487 _ForwardIterator
1488 __parse_extended_reg_exp(_ForwardIterator __first, _ForwardIterator __last);
1489 template <class _ForwardIterator>
1490 _ForwardIterator
1491 __parse_ERE_branch(_ForwardIterator __first, _ForwardIterator __last);
1492 template <class _ForwardIterator>
1493 _ForwardIterator
1494 __parse_ERE_expression(_ForwardIterator __first, _ForwardIterator __last);
1495 template <class _ForwardIterator>
1496 _ForwardIterator
1497 __parse_one_char_or_coll_elem_ERE(_ForwardIterator __first, _ForwardIterator __last);
1498 template <class _ForwardIterator>
1499 _ForwardIterator
1500 __parse_ORD_CHAR_ERE(_ForwardIterator __first, _ForwardIterator __last);
1501 template <class _ForwardIterator>
1502 _ForwardIterator
1503 __parse_QUOTED_CHAR_ERE(_ForwardIterator __first, _ForwardIterator __last);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001504
Howard Hinnant0de86b62010-06-25 20:56:08 +00001505 void __push_l_anchor() {}
1506 void __push_r_anchor() {}
1507 void __push_match_any() {}
1508 void __push_greedy_inf_repeat(int __min) {}
1509 void __push_exact_repeat(int __count) {}
1510 void __push_repeat(int __min, int __max) {}
1511 void __start_nonmatching_list() {}
1512 void __start_matching_list() {}
1513 void __end_nonmatching_list() {}
1514 void __end_matching_list() {}
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001515 void __push_char(value_type __c);
Howard Hinnant0de86b62010-06-25 20:56:08 +00001516 void __push_char(const typename _Traits::string_type& __c) {}
1517 void __push_range() {}
1518 void __push_class_type(typename _Traits::char_class_type) {}
1519 void __push_back_ref(int __i) {}
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001520 void __push_alternation() {}
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001521};
1522
1523template <class _CharT, class _Traits>
1524inline
1525basic_regex<_CharT, _Traits>::basic_regex()
1526 : __traits_(), __flags_(), __marked_count_(0)
1527{
1528}
1529
1530template <class _CharT, class _Traits>
1531basic_regex<_CharT, _Traits>::~basic_regex()
1532{
1533}
1534
1535template <class _CharT, class _Traits>
1536template <class _ForwardIterator>
1537void
1538basic_regex<_CharT, _Traits>::__parse(_ForwardIterator __first,
1539 _ForwardIterator __last)
1540{
1541 switch (__flags_ & 0x3F0)
1542 {
1543 case ECMAScript:
1544 break;
1545 case basic:
1546 __parse_basic_reg_exp(__first, __last);
1547 break;
1548 case extended:
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001549 __parse_extended_reg_exp(__first, __last);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001550 break;
1551 case awk:
1552 break;
1553 case grep:
1554 break;
1555 case egrep:
1556 break;
1557 default:
1558 throw regex_error(regex_constants::error_temp);
1559 }
1560}
1561
1562template <class _CharT, class _Traits>
1563template <class _ForwardIterator>
1564_ForwardIterator
1565basic_regex<_CharT, _Traits>::__parse_basic_reg_exp(_ForwardIterator __first,
1566 _ForwardIterator __last)
1567{
1568 if (__first != __last)
1569 {
1570 if (*__first == '^')
1571 {
1572 __push_l_anchor();
1573 ++__first;
1574 }
1575 if (__first != __last)
1576 {
1577 __first = __parse_RE_expression(__first, __last);
1578 if (__first != __last)
1579 {
1580 _ForwardIterator __temp = next(__first);
1581 if (__temp == __last && *__first == '$')
1582 {
1583 __push_r_anchor();
1584 ++__first;
1585 }
1586 }
1587 }
1588 if (__first != __last)
1589 throw regex_error(regex_constants::error_temp);
1590 }
1591 return __first;
1592}
1593
1594template <class _CharT, class _Traits>
1595template <class _ForwardIterator>
1596_ForwardIterator
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001597basic_regex<_CharT, _Traits>::__parse_extended_reg_exp(_ForwardIterator __first,
1598 _ForwardIterator __last)
1599{
1600 while (true)
1601 {
1602 _ForwardIterator __temp = __parse_ERE_branch(__first, __last);
1603 if (__temp == __first)
1604 throw regex_error(regex_constants::error_temp);
1605 __first = __temp;
1606 if (__first == __last)
1607 break;
1608 if (*__first != '|')
1609 throw regex_error(regex_constants::error_temp);
1610 __push_alternation();
1611 ++__first;
1612 }
1613 return __first;
1614}
1615
1616template <class _CharT, class _Traits>
1617template <class _ForwardIterator>
1618_ForwardIterator
1619basic_regex<_CharT, _Traits>::__parse_ERE_branch(_ForwardIterator __first,
1620 _ForwardIterator __last)
1621{
1622 _ForwardIterator __temp = __parse_ERE_expression(__first, __last);
1623 if (__temp == __first)
1624 throw regex_error(regex_constants::error_temp);
1625 do
1626 {
1627 __first = __temp;
1628 __temp = __parse_ERE_expression(__first, __last);
1629 } while (__temp != __first);
1630 return __first;
1631}
1632
1633template <class _CharT, class _Traits>
1634template <class _ForwardIterator>
1635_ForwardIterator
1636basic_regex<_CharT, _Traits>::__parse_ERE_expression(_ForwardIterator __first,
1637 _ForwardIterator __last)
1638{
1639 _ForwardIterator __temp = __parse_one_char_or_coll_elem_ERE(__first, __last);
1640 if (__temp == __first && __temp != __last)
1641 {
1642 switch (*__temp)
1643 {
1644 case '^':
1645 __push_l_anchor();
1646 ++__temp;
1647 break;
1648 case '$':
1649 __push_r_anchor();
1650 ++__temp;
1651 break;
1652 case '(':
1653 ++__marked_count_;
1654 ++__open_count_;
1655 __temp = __parse_extended_reg_exp(++__temp, __last);
1656 if (__temp == __last || *__temp != ')')
1657 throw regex_error(regex_constants::error_paren);
1658 --__open_count_;
1659 ++__temp;
1660 break;
1661 }
1662 }
1663 if (__temp != __first)
1664 __temp = __parse_ERE_dupl_symbol(__temp, __last);
1665 __first = __temp;
1666 return __first;
1667}
1668
1669template <class _CharT, class _Traits>
1670template <class _ForwardIterator>
1671_ForwardIterator
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001672basic_regex<_CharT, _Traits>::__parse_RE_expression(_ForwardIterator __first,
1673 _ForwardIterator __last)
1674{
1675 while (true)
1676 {
1677 _ForwardIterator __temp = __parse_simple_RE(__first, __last);
1678 if (__temp == __first)
1679 break;
1680 __first = __temp;
1681 }
1682 return __first;
1683}
1684
1685template <class _CharT, class _Traits>
1686template <class _ForwardIterator>
1687_ForwardIterator
1688basic_regex<_CharT, _Traits>::__parse_simple_RE(_ForwardIterator __first,
1689 _ForwardIterator __last)
1690{
1691 if (__first != __last)
1692 {
1693 _ForwardIterator __temp = __parse_nondupl_RE(__first, __last);
1694 if (__temp != __first)
1695 {
1696 __first = __temp;
1697 __first = __parse_RE_dupl_symbol(__first, __last);
1698 }
1699 }
1700 return __first;
1701}
1702
1703template <class _CharT, class _Traits>
1704template <class _ForwardIterator>
1705_ForwardIterator
1706basic_regex<_CharT, _Traits>::__parse_nondupl_RE(_ForwardIterator __first,
1707 _ForwardIterator __last)
1708{
1709 _ForwardIterator __temp = __first;
1710 __first = __parse_one_char_or_coll_elem_RE(__first, __last);
1711 if (__temp == __first)
1712 {
1713 __temp = __parse_Back_open_paren(__first, __last);
1714 if (__temp != __first)
1715 {
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001716 ++__marked_count_;
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001717 __first = __parse_RE_expression(__temp, __last);
1718 __temp = __parse_Back_close_paren(__first, __last);
1719 if (__temp == __first)
1720 throw regex_error(regex_constants::error_paren);
1721 __first = __temp;
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001722 }
1723 else
1724 __first = __parse_BACKREF(__first, __last);
1725 }
1726 return __first;
1727}
1728
1729template <class _CharT, class _Traits>
1730template <class _ForwardIterator>
1731_ForwardIterator
1732basic_regex<_CharT, _Traits>::__parse_one_char_or_coll_elem_RE(
1733 _ForwardIterator __first,
1734 _ForwardIterator __last)
1735{
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001736 _ForwardIterator __temp = __parse_ORD_CHAR(__first, __last);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001737 if (__temp == __first)
1738 {
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001739 __temp = __parse_QUOTED_CHAR(__first, __last);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001740 if (__temp == __first)
1741 {
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001742 if (__temp != __last && *__temp == '.')
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001743 {
1744 __push_match_any();
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001745 ++__temp;
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001746 }
1747 else
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001748 __temp = __parse_bracket_expression(__first, __last);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001749 }
1750 }
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001751 __first = __temp;
1752 return __first;
1753}
1754
1755template <class _CharT, class _Traits>
1756template <class _ForwardIterator>
1757_ForwardIterator
1758basic_regex<_CharT, _Traits>::__parse_one_char_or_coll_elem_ERE(
1759 _ForwardIterator __first,
1760 _ForwardIterator __last)
1761{
1762 _ForwardIterator __temp = __parse_ORD_CHAR_ERE(__first, __last);
1763 if (__temp == __first)
1764 {
1765 __temp = __parse_QUOTED_CHAR_ERE(__first, __last);
1766 if (__temp == __first)
1767 {
1768 if (__temp != __last && *__temp == '.')
1769 {
1770 __push_match_any();
1771 ++__temp;
1772 }
1773 else
1774 __temp = __parse_bracket_expression(__first, __last);
1775 }
1776 }
1777 __first = __temp;
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001778 return __first;
1779}
1780
1781template <class _CharT, class _Traits>
1782template <class _ForwardIterator>
1783_ForwardIterator
1784basic_regex<_CharT, _Traits>::__parse_Back_open_paren(_ForwardIterator __first,
1785 _ForwardIterator __last)
1786{
1787 if (__first != __last)
1788 {
1789 _ForwardIterator __temp = next(__first);
1790 if (__temp != __last)
1791 {
1792 if (*__first == '\\' && *__temp == '(')
1793 __first = ++__temp;
1794 }
1795 }
1796 return __first;
1797}
1798
1799template <class _CharT, class _Traits>
1800template <class _ForwardIterator>
1801_ForwardIterator
1802basic_regex<_CharT, _Traits>::__parse_Back_close_paren(_ForwardIterator __first,
1803 _ForwardIterator __last)
1804{
1805 if (__first != __last)
1806 {
1807 _ForwardIterator __temp = next(__first);
1808 if (__temp != __last)
1809 {
1810 if (*__first == '\\' && *__temp == ')')
1811 __first = ++__temp;
1812 }
1813 }
1814 return __first;
1815}
1816
1817template <class _CharT, class _Traits>
1818template <class _ForwardIterator>
1819_ForwardIterator
1820basic_regex<_CharT, _Traits>::__parse_Back_open_brace(_ForwardIterator __first,
1821 _ForwardIterator __last)
1822{
1823 if (__first != __last)
1824 {
1825 _ForwardIterator __temp = next(__first);
1826 if (__temp != __last)
1827 {
1828 if (*__first == '\\' && *__temp == '{')
1829 __first = ++__temp;
1830 }
1831 }
1832 return __first;
1833}
1834
1835template <class _CharT, class _Traits>
1836template <class _ForwardIterator>
1837_ForwardIterator
1838basic_regex<_CharT, _Traits>::__parse_Back_close_brace(_ForwardIterator __first,
1839 _ForwardIterator __last)
1840{
1841 if (__first != __last)
1842 {
1843 _ForwardIterator __temp = next(__first);
1844 if (__temp != __last)
1845 {
1846 if (*__first == '\\' && *__temp == '}')
1847 __first = ++__temp;
1848 }
1849 }
1850 return __first;
1851}
1852
1853template <class _CharT, class _Traits>
1854template <class _ForwardIterator>
1855_ForwardIterator
1856basic_regex<_CharT, _Traits>::__parse_BACKREF(_ForwardIterator __first,
1857 _ForwardIterator __last)
1858{
1859 if (__first != __last)
1860 {
1861 _ForwardIterator __temp = next(__first);
1862 if (__temp != __last)
1863 {
1864 if (*__first == '\\' && '1' <= *__temp && *__temp <= '9')
1865 {
1866 __push_back_ref(*__temp - '0');
1867 __first = ++__temp;
1868 }
1869 }
1870 }
1871 return __first;
1872}
1873
1874template <class _CharT, class _Traits>
1875template <class _ForwardIterator>
1876_ForwardIterator
1877basic_regex<_CharT, _Traits>::__parse_ORD_CHAR(_ForwardIterator __first,
1878 _ForwardIterator __last)
1879{
1880 if (__first != __last)
1881 {
1882 _ForwardIterator __temp = next(__first);
1883 if (__temp == __last && *__first == '$')
1884 return __first;
1885 // Not called inside a bracket
1886 if (*__first == '.' || *__first == '\\' || *__first == '[')
1887 return __first;
Howard Hinnant0de86b62010-06-25 20:56:08 +00001888 __push_char(*__first);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001889 ++__first;
1890 }
1891 return __first;
1892}
1893
1894template <class _CharT, class _Traits>
1895template <class _ForwardIterator>
1896_ForwardIterator
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001897basic_regex<_CharT, _Traits>::__parse_ORD_CHAR_ERE(_ForwardIterator __first,
1898 _ForwardIterator __last)
1899{
1900 if (__first != __last)
1901 {
1902 switch (*__first)
1903 {
1904 case '^':
1905 case '.':
1906 case '[':
1907 case '$':
1908 case '(':
1909 case '|':
1910 case '*':
1911 case '+':
1912 case '?':
1913 case '{':
1914 case '\\':
1915 break;
1916 case ')':
1917 if (__open_count_ == 0)
1918 {
1919 __push_char(*__first);
1920 ++__first;
1921 }
1922 break;
1923 default:
1924 __push_char(*__first);
1925 ++__first;
1926 break;
1927 }
1928 }
1929 return __first;
1930}
1931
1932template <class _CharT, class _Traits>
1933template <class _ForwardIterator>
1934_ForwardIterator
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001935basic_regex<_CharT, _Traits>::__parse_QUOTED_CHAR(_ForwardIterator __first,
1936 _ForwardIterator __last)
1937{
1938 if (__first != __last)
1939 {
1940 _ForwardIterator __temp = next(__first);
1941 if (__temp != __last)
1942 {
1943 if (*__first == '\\')
1944 {
1945 switch (*__temp)
1946 {
1947 case '^':
1948 case '.':
1949 case '*':
1950 case '[':
1951 case '$':
1952 case '\\':
Howard Hinnant0de86b62010-06-25 20:56:08 +00001953 __push_char(*__temp);
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00001954 __first = ++__temp;
1955 break;
1956 }
1957 }
1958 }
1959 }
1960 return __first;
1961}
1962
1963template <class _CharT, class _Traits>
1964template <class _ForwardIterator>
1965_ForwardIterator
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00001966basic_regex<_CharT, _Traits>::__parse_QUOTED_CHAR_ERE(_ForwardIterator __first,
1967 _ForwardIterator __last)
1968{
1969 if (__first != __last)
1970 {
1971 _ForwardIterator __temp = next(__first);
1972 if (__temp != __last)
1973 {
1974 if (*__first == '\\')
1975 {
1976 switch (*__temp)
1977 {
1978 case '^':
1979 case '.':
1980 case '*':
1981 case '[':
1982 case '$':
1983 case '\\':
1984 case '(':
1985 case ')':
1986 case '|':
1987 case '+':
1988 case '?':
1989 case '{':
1990 __push_char(*__temp);
1991 __first = ++__temp;
1992 break;
1993 }
1994 }
1995 }
1996 }
1997 return __first;
1998}
1999
2000template <class _CharT, class _Traits>
2001template <class _ForwardIterator>
2002_ForwardIterator
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00002003basic_regex<_CharT, _Traits>::__parse_RE_dupl_symbol(_ForwardIterator __first,
2004 _ForwardIterator __last)
2005{
2006 if (__first != __last)
2007 {
Howard Hinnant0de86b62010-06-25 20:56:08 +00002008 if (*__first == '*')
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00002009 {
2010 __push_greedy_inf_repeat(0);
2011 ++__first;
2012 }
2013 else
2014 {
2015 _ForwardIterator __temp = __parse_Back_open_brace(__first, __last);
2016 if (__temp != __first)
2017 {
2018 int __min = 0;
2019 __first = __temp;
2020 __temp = __parse_DUP_COUNT(__first, __last, __min);
2021 if (__temp == __first)
2022 throw regex_error(regex_constants::error_badbrace);
2023 __first = __temp;
2024 if (__first == __last)
2025 throw regex_error(regex_constants::error_brace);
2026 if (*__first != ',')
2027 {
2028 __temp = __parse_Back_close_brace(__first, __last);
2029 if (__temp == __first)
2030 throw regex_error(regex_constants::error_brace);
2031 __push_exact_repeat(__min);
2032 __first = __temp;
2033 }
2034 else
2035 {
2036 ++__first; // consume ','
2037 int __max = -1;
2038 __first = __parse_DUP_COUNT(__first, __last, __max);
2039 __temp = __parse_Back_close_brace(__first, __last);
2040 if (__temp == __first)
2041 throw regex_error(regex_constants::error_brace);
2042 if (__max == -1)
2043 __push_greedy_inf_repeat(__min);
2044 else
2045 {
2046 if (__max < __min)
2047 throw regex_error(regex_constants::error_badbrace);
2048 __push_repeat(__min, __max);
2049 }
2050 __first = __temp;
2051 }
2052 }
2053 }
2054 }
2055 return __first;
2056}
2057
Howard Hinnant0de86b62010-06-25 20:56:08 +00002058template <class _CharT, class _Traits>
2059template <class _ForwardIterator>
2060_ForwardIterator
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00002061basic_regex<_CharT, _Traits>::__parse_ERE_dupl_symbol(_ForwardIterator __first,
2062 _ForwardIterator __last)
2063{
2064 if (__first != __last)
2065 {
2066 switch (*__first)
2067 {
2068 case '*':
2069 __push_greedy_inf_repeat(0);
2070 ++__first;
2071 break;
2072 case '+':
2073 __push_greedy_inf_repeat(1);
2074 ++__first;
2075 break;
2076 case '?':
2077 __push_repeat(0, 1);
2078 ++__first;
2079 break;
2080 case '{':
2081 {
2082 int __min;
2083 _ForwardIterator __temp = __parse_DUP_COUNT(__first, __last, __min);
2084 if (__temp == __first)
2085 throw regex_error(regex_constants::error_badbrace);
2086 __first = __temp;
2087 if (__first == __last)
2088 throw regex_error(regex_constants::error_brace);
2089 switch (*__first)
2090 {
2091 case '}':
2092 __push_exact_repeat(__min);
2093 ++__first;
2094 break;
2095 case ',':
2096 if (++__first == __last)
2097 throw regex_error(regex_constants::error_badbrace);
2098 if (*__first == '}')
2099 {
2100 __push_greedy_inf_repeat(__min);
2101 ++__first;
2102 }
2103 else
2104 {
2105 int __max;
2106 __temp = __parse_DUP_COUNT(__first, __last, __max);
2107 if (__temp == __first)
2108 throw regex_error(regex_constants::error_brace);
2109 __first = __temp;
2110 if (__first == __last || *__first != '}')
2111 throw regex_error(regex_constants::error_brace);
2112 ++__first;
2113 if (__max < __min)
2114 throw regex_error(regex_constants::error_badbrace);
2115 __push_repeat(__min, __max);
2116 }
2117 default:
2118 throw regex_error(regex_constants::error_badbrace);
2119 }
2120 }
2121 break;
2122 }
2123 }
2124 return __first;
2125}
2126
2127template <class _CharT, class _Traits>
2128template <class _ForwardIterator>
2129_ForwardIterator
Howard Hinnant0de86b62010-06-25 20:56:08 +00002130basic_regex<_CharT, _Traits>::__parse_bracket_expression(_ForwardIterator __first,
2131 _ForwardIterator __last)
2132{
2133 if (__first != __last && *__first == '[')
2134 {
2135 if (++__first == __last)
2136 throw regex_error(regex_constants::error_brack);
2137 bool __non_matching = false;
2138 if (*__first == '^')
2139 {
2140 ++__first;
2141 __non_matching = true;
2142 __start_nonmatching_list();
2143 }
2144 else
2145 __start_matching_list();
2146 if (__first == __last)
2147 throw regex_error(regex_constants::error_brack);
2148 if (*__first == ']')
2149 {
2150 __push_char(']');
2151 ++__first;
2152 }
2153 __first = __parse_follow_list(__first, __last);
2154 if (__first == __last)
2155 throw regex_error(regex_constants::error_brack);
2156 if (*__first == '-')
2157 {
2158 __push_char('-');
2159 ++__first;
2160 }
2161 if (__first == __last || *__first != ']')
2162 throw regex_error(regex_constants::error_brack);
2163 if (__non_matching)
2164 __end_nonmatching_list();
2165 else
2166 __end_matching_list();
2167 ++__first;
2168 }
2169 return __first;
2170}
2171
2172template <class _CharT, class _Traits>
2173template <class _ForwardIterator>
2174_ForwardIterator
2175basic_regex<_CharT, _Traits>::__parse_follow_list(_ForwardIterator __first,
2176 _ForwardIterator __last)
2177{
2178 if (__first != __last)
2179 {
2180 while (true)
2181 {
2182 _ForwardIterator __temp = __parse_expression_term(__first, __last);
2183 if (__temp == __first)
2184 break;
2185 __first = __temp;
2186 }
2187 }
2188 return __first;
2189}
2190
2191template <class _CharT, class _Traits>
2192template <class _ForwardIterator>
2193_ForwardIterator
2194basic_regex<_CharT, _Traits>::__parse_expression_term(_ForwardIterator __first,
2195 _ForwardIterator __last)
2196{
2197 if (__first != __last && *__first != ']')
2198 {
2199 bool __parsed_one = false;
2200 _ForwardIterator __temp = next(__first);
2201 if (__temp != __last && *__first == '[')
2202 {
2203 if (*__temp == '=')
2204 return __parse_equivalence_class(++__temp, __last);
2205 else if (*__temp == ':')
2206 return __parse_character_class(++__temp, __last);
2207 else if (*__temp == '.')
2208 {
2209 __first = __parse_collating_symbol(++__temp, __last);
2210 __parsed_one = true;
2211 }
2212 }
2213 if (!__parsed_one)
2214 {
2215 __push_char(*__first);
2216 ++__first;
2217 }
2218 if (__first != __last && *__first != ']')
2219 {
2220 __temp = next(__first);
2221 if (__temp != __last && *__first == '-' && *__temp != ']')
2222 {
2223 // parse a range
2224 __first = __temp;
2225 ++__temp;
2226 if (__temp != __last && *__first == '[' && *__temp == '.')
2227 __first = __parse_collating_symbol(++__temp, __last);
2228 else
2229 {
2230 __push_char(*__first);
2231 ++__first;
2232 }
2233 __push_range();
2234 }
2235 }
2236 }
2237 return __first;
2238}
2239
2240template <class _CharT, class _Traits>
2241template <class _ForwardIterator>
2242_ForwardIterator
2243basic_regex<_CharT, _Traits>::__parse_equivalence_class(_ForwardIterator __first,
2244 _ForwardIterator __last)
2245{
2246 // Found [=
2247 // This means =] must exist
2248 value_type _Equal_close[2] = {'=', ']'};
2249 _ForwardIterator __temp = _STD::search(__first, __last, _Equal_close,
2250 _Equal_close+2);
2251 if (__temp == __last)
2252 throw regex_error(regex_constants::error_brack);
2253 // [__first, __temp) contains all text in [= ... =]
2254 typedef typename _Traits::string_type string_type;
2255 string_type __collate_name =
2256 __traits_.lookup_collatename(__first, __temp);
2257 if (__collate_name.empty())
2258 throw regex_error(regex_constants::error_brack);
2259 string_type __equiv_name =
2260 __traits_.transform_primary(__collate_name.begin(),
2261 __collate_name.end());
2262 if (!__equiv_name.empty())
2263 __push_char(__equiv_name);
2264 else
2265 __push_char(__collate_name);
2266 __first = next(__temp, 2);
2267 return __first;
2268}
2269
2270template <class _CharT, class _Traits>
2271template <class _ForwardIterator>
2272_ForwardIterator
2273basic_regex<_CharT, _Traits>::__parse_character_class(_ForwardIterator __first,
2274 _ForwardIterator __last)
2275{
2276 // Found [:
2277 // This means :] must exist
2278 value_type _Colon_close[2] = {':', ']'};
2279 _ForwardIterator __temp = _STD::search(__first, __last, _Colon_close,
2280 _Colon_close+2);
2281 if (__temp == __last)
2282 throw regex_error(regex_constants::error_brack);
2283 // [__first, __temp) contains all text in [: ... :]
2284 typedef typename _Traits::char_class_type char_class_type;
2285 char_class_type __class_type =
2286 __traits_.lookup_classname(__first, __temp, __flags_ & icase);
2287 if (__class_type == 0)
2288 throw regex_error(regex_constants::error_brack);
2289 __push_class_type(__class_type);
2290 __first = next(__temp, 2);
2291 return __first;
2292}
2293
2294template <class _CharT, class _Traits>
2295template <class _ForwardIterator>
2296_ForwardIterator
2297basic_regex<_CharT, _Traits>::__parse_collating_symbol(_ForwardIterator __first,
2298 _ForwardIterator __last)
2299{
2300 // Found [.
2301 // This means .] must exist
2302 value_type _Dot_close[2] = {'.', ']'};
2303 _ForwardIterator __temp = _STD::search(__first, __last, _Dot_close,
2304 _Dot_close+2);
2305 if (__temp == __last)
2306 throw regex_error(regex_constants::error_brack);
2307 // [__first, __temp) contains all text in [. ... .]
2308 typedef typename _Traits::string_type string_type;
2309 string_type __collate_name =
2310 __traits_.lookup_collatename(__first, __temp);
2311 if (__collate_name.empty())
2312 throw regex_error(regex_constants::error_brack);
2313 __push_char(__collate_name);
2314 __first = next(__temp, 2);
2315 return __first;
2316}
2317
2318template <class _CharT, class _Traits>
2319template <class _ForwardIterator>
2320_ForwardIterator
2321basic_regex<_CharT, _Traits>::__parse_DUP_COUNT(_ForwardIterator __first,
2322 _ForwardIterator __last,
2323 int& __c)
2324{
2325 if (__first != __last && '0' <= *__first && *__first <= '9')
2326 {
2327 __c = *__first - '0';
2328 for (++__first; __first != __last && '0' <= *__first && *__first <= '9';
2329 ++__first)
2330 {
2331 __c *= 10;
2332 __c += *__first - '0';
2333 }
2334 }
2335 return __first;
2336}
2337
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00002338template <class _CharT, class _Traits>
2339void
2340basic_regex<_CharT, _Traits>::__push_char(value_type __c)
2341{
2342 unique_ptr<__state<_CharT> > __new_end(new __state<_CharT>);
2343 unique_ptr<__transition<_CharT> > __new_transition(
2344 new __match_char<_CharT>(__c, true, __new_end.get()));
2345 __state<_CharT>* __e = __new_end.release();
2346 if (__end_ == nullptr)
2347 {
2348 __start_.reset(new __state<_CharT>);
2349 __end_ = __start_.get();
2350 }
2351 __end_->__add_one(__new_transition.release());
2352 __end_ = __e;
2353}
2354
Howard Hinnant8c2c18d2010-06-24 21:28:00 +00002355typedef basic_regex<char> regex;
2356typedef basic_regex<wchar_t> wregex;
2357
Howard Hinnantcd85b9e2010-06-29 18:37:43 +00002358// sub_match
2359
2360template <class _BidirectionalIterator>
2361class sub_match
2362 : public pair<_BidirectionalIterator, _BidirectionalIterator>
2363{
2364public:
2365 typedef _BidirectionalIterator iterator;
2366 typedef typename iterator_traits<iterator>::value_type value_type;
2367 typedef typename iterator_traits<iterator>::difference_type difference_type;
2368 typedef basic_string<value_type> string_type;
2369
2370 bool matched;
2371
2372 difference_type length() const
2373 {return matched ? _STD::distance(this->first, this->second) : 0;}
2374 string_type str() const
2375 {return matched ? string_type(this->first, this->second) : string_type();}
2376 operator string_type() const
2377 {return str();}
2378
2379 int compare(const sub_match& __s) const
2380 {return str().compare(__s.str());}
2381 int compare(const string_type& __s) const
2382 {return str().compare(__s);}
2383 int compare(const value_type* __s) const
2384 {return str().compare(__s);}
2385};
2386
2387typedef sub_match<const char*> csub_match;
2388typedef sub_match<const wchar_t*> wcsub_match;
2389typedef sub_match<string::const_iterator> ssub_match;
2390typedef sub_match<wstring::const_iterator> wssub_match;
2391
2392template <class _BiIter>
2393inline _LIBCPP_INLINE_VISIBILITY
2394bool
2395operator==(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2396{
2397 return __x.compare(__y) == 0;
2398}
2399
2400template <class _BiIter>
2401inline _LIBCPP_INLINE_VISIBILITY
2402bool
2403operator!=(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2404{
2405 return !(__x == __y);
2406}
2407
2408template <class _BiIter>
2409inline _LIBCPP_INLINE_VISIBILITY
2410bool
2411operator<(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2412{
2413 return __x.compare(__y) < 0;
2414}
2415
2416template <class _BiIter>
2417inline _LIBCPP_INLINE_VISIBILITY
2418bool
2419operator<=(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2420{
2421 return !(__y < __x);
2422}
2423
2424template <class _BiIter>
2425inline _LIBCPP_INLINE_VISIBILITY
2426bool
2427operator>=(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2428{
2429 return !(__x < __y);
2430}
2431
2432template <class _BiIter>
2433inline _LIBCPP_INLINE_VISIBILITY
2434bool
2435operator>(const sub_match<_BiIter>& __x, const sub_match<_BiIter>& __y)
2436{
2437 return __y < __x;
2438}
2439
2440template <class _BiIter, class _ST, class _SA>
2441inline _LIBCPP_INLINE_VISIBILITY
2442bool
2443operator==(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2444 const sub_match<_BiIter>& __y)
2445{
2446 return __y.compare(__x.c_str()) == 0;
2447}
2448
2449template <class _BiIter, class _ST, class _SA>
2450inline _LIBCPP_INLINE_VISIBILITY
2451bool
2452operator!=(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2453 const sub_match<_BiIter>& __y)
2454{
2455 return !(__x == __y);
2456}
2457
2458template <class _BiIter, class _ST, class _SA>
2459inline _LIBCPP_INLINE_VISIBILITY
2460bool
2461operator<(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2462 const sub_match<_BiIter>& __y)
2463{
2464 return __y.compare(__x.c_str()) > 0;
2465}
2466
2467template <class _BiIter, class _ST, class _SA>
2468inline _LIBCPP_INLINE_VISIBILITY
2469bool
2470operator>(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2471 const sub_match<_BiIter>& __y)
2472{
2473 return __y < __x;
2474}
2475
2476template <class _BiIter, class _ST, class _SA>
2477inline _LIBCPP_INLINE_VISIBILITY
2478bool operator>=(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2479 const sub_match<_BiIter>& __y)
2480{
2481 return !(__x < __y);
2482}
2483
2484template <class _BiIter, class _ST, class _SA>
2485inline _LIBCPP_INLINE_VISIBILITY
2486bool
2487operator<=(const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __x,
2488 const sub_match<_BiIter>& __y)
2489{
2490 return !(__y < __x);
2491}
2492
2493template <class _BiIter, class _ST, class _SA>
2494inline _LIBCPP_INLINE_VISIBILITY
2495bool
2496operator==(const sub_match<_BiIter>& __x,
2497 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2498{
2499 return __x.compare(__y.c_str()) == 0;
2500}
2501
2502template <class _BiIter, class _ST, class _SA>
2503inline _LIBCPP_INLINE_VISIBILITY
2504bool
2505operator!=(const sub_match<_BiIter>& __x,
2506 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2507{
2508 return !(__x == __y);
2509}
2510
2511template <class _BiIter, class _ST, class _SA>
2512inline _LIBCPP_INLINE_VISIBILITY
2513bool
2514operator<(const sub_match<_BiIter>& __x,
2515 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2516{
2517 return __x.compare(__y.c_str()) < 0;
2518}
2519
2520template <class _BiIter, class _ST, class _SA>
2521inline _LIBCPP_INLINE_VISIBILITY
2522bool operator>(const sub_match<_BiIter>& __x,
2523 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2524{
2525 return __y < __x;
2526}
2527
2528template <class _BiIter, class _ST, class _SA>
2529inline _LIBCPP_INLINE_VISIBILITY
2530bool
2531operator>=(const sub_match<_BiIter>& __x,
2532 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2533{
2534 return !(__x < __y);
2535}
2536
2537template <class _BiIter, class _ST, class _SA>
2538inline _LIBCPP_INLINE_VISIBILITY
2539bool
2540operator<=(const sub_match<_BiIter>& __x,
2541 const basic_string<typename iterator_traits<_BiIter>::value_type, _ST, _SA>& __y)
2542{
2543 return !(__y < __x);
2544}
2545
2546template <class _BiIter>
2547inline _LIBCPP_INLINE_VISIBILITY
2548bool
2549operator==(typename iterator_traits<_BiIter>::value_type const* __x,
2550 const sub_match<_BiIter>& __y)
2551{
2552 return __y.compare(__x) == 0;
2553}
2554
2555template <class _BiIter>
2556inline _LIBCPP_INLINE_VISIBILITY
2557bool
2558operator!=(typename iterator_traits<_BiIter>::value_type const* __x,
2559 const sub_match<_BiIter>& __y)
2560{
2561 return !(__x == __y);
2562}
2563
2564template <class _BiIter>
2565inline _LIBCPP_INLINE_VISIBILITY
2566bool
2567operator<(typename iterator_traits<_BiIter>::value_type const* __x,
2568 const sub_match<_BiIter>& __y)
2569{
2570 return __y.compare(__x) > 0;
2571}
2572
2573template <class _BiIter>
2574inline _LIBCPP_INLINE_VISIBILITY
2575bool
2576operator>(typename iterator_traits<_BiIter>::value_type const* __x,
2577 const sub_match<_BiIter>& __y)
2578{
2579 return __y < __x;
2580}
2581
2582template <class _BiIter>
2583inline _LIBCPP_INLINE_VISIBILITY
2584bool
2585operator>=(typename iterator_traits<_BiIter>::value_type const* __x,
2586 const sub_match<_BiIter>& __y)
2587{
2588 return !(__x < __y);
2589}
2590
2591template <class _BiIter>
2592inline _LIBCPP_INLINE_VISIBILITY
2593bool
2594operator<=(typename iterator_traits<_BiIter>::value_type const* __x,
2595 const sub_match<_BiIter>& __y)
2596{
2597 return !(__y < __x);
2598}
2599
2600template <class _BiIter>
2601inline _LIBCPP_INLINE_VISIBILITY
2602bool
2603operator==(const sub_match<_BiIter>& __x,
2604 typename iterator_traits<_BiIter>::value_type const* __y)
2605{
2606 return __x.compare(__y) == 0;
2607}
2608
2609template <class _BiIter>
2610inline _LIBCPP_INLINE_VISIBILITY
2611bool
2612operator!=(const sub_match<_BiIter>& __x,
2613 typename iterator_traits<_BiIter>::value_type const* __y)
2614{
2615 return !(__x == __y);
2616}
2617
2618template <class _BiIter>
2619inline _LIBCPP_INLINE_VISIBILITY
2620bool
2621operator<(const sub_match<_BiIter>& __x,
2622 typename iterator_traits<_BiIter>::value_type const* __y)
2623{
2624 return __x.compare(__y) < 0;
2625}
2626
2627template <class _BiIter>
2628inline _LIBCPP_INLINE_VISIBILITY
2629bool
2630operator>(const sub_match<_BiIter>& __x,
2631 typename iterator_traits<_BiIter>::value_type const* __y)
2632{
2633 return __y < __x;
2634}
2635
2636template <class _BiIter>
2637inline _LIBCPP_INLINE_VISIBILITY
2638bool
2639operator>=(const sub_match<_BiIter>& __x,
2640 typename iterator_traits<_BiIter>::value_type const* __y)
2641{
2642 return !(__x < __y);
2643}
2644
2645template <class _BiIter>
2646inline _LIBCPP_INLINE_VISIBILITY
2647bool
2648operator<=(const sub_match<_BiIter>& __x,
2649 typename iterator_traits<_BiIter>::value_type const* __y)
2650{
2651 return !(__y < __x);
2652}
2653
2654template <class _BiIter>
2655inline _LIBCPP_INLINE_VISIBILITY
2656bool
2657operator==(typename iterator_traits<_BiIter>::value_type const& __x,
2658 const sub_match<_BiIter>& __y)
2659{
2660 typedef basic_string<typename iterator_traits<_BiIter>::value_type> string_type;
2661 return __y.compare(string_type(1, __x)) == 0;
2662}
2663
2664template <class _BiIter>
2665inline _LIBCPP_INLINE_VISIBILITY
2666bool
2667operator!=(typename iterator_traits<_BiIter>::value_type const& __x,
2668 const sub_match<_BiIter>& __y)
2669{
2670 return !(__x == __y);
2671}
2672
2673template <class _BiIter>
2674inline _LIBCPP_INLINE_VISIBILITY
2675bool
2676operator<(typename iterator_traits<_BiIter>::value_type const& __x,
2677 const sub_match<_BiIter>& __y)
2678{
2679 typedef basic_string<typename iterator_traits<_BiIter>::value_type> string_type;
2680 return __y.compare(string_type(1, __x)) > 0;
2681}
2682
2683template <class _BiIter>
2684inline _LIBCPP_INLINE_VISIBILITY
2685bool
2686operator>(typename iterator_traits<_BiIter>::value_type const& __x,
2687 const sub_match<_BiIter>& __y)
2688{
2689 return __y < __x;
2690}
2691
2692template <class _BiIter>
2693inline _LIBCPP_INLINE_VISIBILITY
2694bool
2695operator>=(typename iterator_traits<_BiIter>::value_type const& __x,
2696 const sub_match<_BiIter>& __y)
2697{
2698 return !(__x < __y);
2699}
2700
2701template <class _BiIter>
2702inline _LIBCPP_INLINE_VISIBILITY
2703bool
2704operator<=(typename iterator_traits<_BiIter>::value_type const& __x,
2705 const sub_match<_BiIter>& __y)
2706{
2707 return !(__y < __x);
2708}
2709
2710template <class _BiIter>
2711inline _LIBCPP_INLINE_VISIBILITY
2712bool
2713operator==(const sub_match<_BiIter>& __x,
2714 typename iterator_traits<_BiIter>::value_type const& __y)
2715{
2716 typedef basic_string<typename iterator_traits<_BiIter>::value_type> string_type;
2717 return __x.compare(string_type(1, __y)) == 0;
2718}
2719
2720template <class _BiIter>
2721inline _LIBCPP_INLINE_VISIBILITY
2722bool
2723operator!=(const sub_match<_BiIter>& __x,
2724 typename iterator_traits<_BiIter>::value_type const& __y)
2725{
2726 return !(__x == __y);
2727}
2728
2729template <class _BiIter>
2730inline _LIBCPP_INLINE_VISIBILITY
2731bool
2732operator<(const sub_match<_BiIter>& __x,
2733 typename iterator_traits<_BiIter>::value_type const& __y)
2734{
2735 typedef basic_string<typename iterator_traits<_BiIter>::value_type> string_type;
2736 return __x.compare(string_type(1, __y)) < 0;
2737}
2738
2739template <class _BiIter>
2740inline _LIBCPP_INLINE_VISIBILITY
2741bool
2742operator>(const sub_match<_BiIter>& __x,
2743 typename iterator_traits<_BiIter>::value_type const& __y)
2744{
2745 return __y < __x;
2746}
2747
2748template <class _BiIter>
2749inline _LIBCPP_INLINE_VISIBILITY
2750bool
2751operator>=(const sub_match<_BiIter>& __x,
2752 typename iterator_traits<_BiIter>::value_type const& __y)
2753{
2754 return !(__x < __y);
2755}
2756
2757template <class _BiIter>
2758inline _LIBCPP_INLINE_VISIBILITY
2759bool
2760operator<=(const sub_match<_BiIter>& __x,
2761 typename iterator_traits<_BiIter>::value_type const& __y)
2762{
2763 return !(__y < __x);
2764}
2765
2766template <class _CharT, class _ST, class _BiIter>
2767inline _LIBCPP_INLINE_VISIBILITY
2768basic_ostream<_CharT, _ST>&
2769operator<<(basic_ostream<_CharT, _ST>& __os, const sub_match<_BiIter>& __m)
2770{
2771 return __os << __m.str();
2772}
2773
Howard Hinnant7e9d84b2010-06-30 00:21:42 +00002774template <class _BidirectionalIterator,
2775 class _Allocator = allocator<sub_match<_BidirectionalIterator> > >
2776class match_results
2777{
2778public:
2779 typedef _Allocator allocator_type;
2780 typedef sub_match<_BidirectionalIterator> value_type;
2781private:
2782 typedef vector<value_type, allocator_type> __container_type;
2783
2784 __container_type __matches_;
2785 value_type __unmatched_;
2786 value_type __prefix_;
2787 value_type __suffix_;
2788public:
2789 typedef const value_type& const_reference;
2790 typedef const_reference reference;
2791 typedef typename __container_type::const_iterator const_iterator;
2792 typedef const_iterator iterator;
2793 typedef typename iterator_traits<_BidirectionalIterator>::difference_type difference_type;
2794 typedef typename allocator_traits<allocator_type>::size_type size_type;
2795 typedef typename iterator_traits<_BidirectionalIterator>::value_type char_type;
2796 typedef basic_string<char_type> string_type;
2797
2798 // construct/copy/destroy:
2799 explicit match_results(const allocator_type& __a = allocator_type());
2800// match_results(const match_results&) = default;
2801// match_results& operator=(const match_results&) = default;
2802#ifdef _LIBCPP_MOVE
2803// match_results(match_results&& __m) = default;
2804// match_results& operator=(match_results&& __m) = default;
2805#endif
2806// ~match_results() = default;
2807
2808 // size:
2809 size_type size() const {return __matches_.size();}
2810 size_type max_size() const {return __matches_.max_size();}
2811 bool empty() const {return size() == 0;}
2812
2813 // element access:
2814 difference_type length(size_type __sub = 0) const
2815 {return (*this)[__sub].length();}
2816 difference_type position(size_type __sub = 0) const
2817 {return _STD::distance(__prefix_.first, (*this)[__sub].first);}
2818 string_type str(size_type __sub = 0) const
2819 {return (*this)[__sub].str();}
2820 const_reference operator[](size_type __n) const
2821 {return __n < __matches_.size() ? __matches_[__n] : __unmatched_;}
2822
2823 const_reference prefix() const {return __prefix_;}
2824 const_reference suffix() const {return __suffix_;}
2825
2826 const_iterator begin() const {return empty() ? __matches_.end() : __matches_.begin() + 1;}
2827 const_iterator end() const {return __matches_.end();}
2828 const_iterator cbegin() const {return empty() ? __matches_.end() : __matches_.begin() + 1;}
2829 const_iterator cend() const {return __matches_.end();}
2830
2831 // format:
2832 template <class _OutputIter>
2833 _OutputIter
2834 format(_OutputIter __out, const char_type* __fmt_first,
2835 const char_type* __fmt_last,
2836 regex_constants::match_flag_type __flags = regex_constants::format_default) const;
2837 template <class _OutputIter, class _ST, class _SA>
2838 _OutputIter
2839 format(_OutputIter __out, const basic_string<char_type, _ST, _SA>& __fmt,
2840 regex_constants::match_flag_type __flags = regex_constants::format_default) const;
2841 template <class _ST, class _SA>
2842 basic_string<char_type, _ST, _SA>
2843 format(const basic_string<char_type, _ST, _SA>& __fmt,
2844 regex_constants::match_flag_type __flags = regex_constants::format_default) const;
2845 string_type
2846 format(const char_type* __fmt,
2847 regex_constants::match_flag_type __flags = regex_constants::format_default) const;
2848
2849 // allocator:
2850 allocator_type get_allocator() const {return __matches_.get_allocator();}
2851
2852 // swap:
2853 void swap(match_results& __m);
2854
2855 template <class _B, class _A, class _C, class _T>
2856 friend
2857 bool
2858 regex_match(_B, _B, match_results<_B, _A>&, const basic_regex<_C, _T>&,
2859 regex_constants::match_flag_type);
2860};
2861
2862template <class _BidirectionalIterator, class _Allocator>
2863match_results<_BidirectionalIterator, _Allocator>::match_results(
2864 const allocator_type& __a)
2865 : __matches_(__a),
2866 __unmatched_(),
2867 __prefix_(),
2868 __suffix_()
2869{
2870}
2871
2872typedef match_results<const char*> cmatch;
2873typedef match_results<const wchar_t*> wcmatch;
2874typedef match_results<string::const_iterator> smatch;
2875typedef match_results<wstring::const_iterator> wsmatch;
2876
2877template <class _BidirectionalIterator, class _Allocator>
2878 bool
2879 operator==(const match_results<_BidirectionalIterator, _Allocator>& __x,
2880 const match_results<_BidirectionalIterator, _Allocator>& __y);
2881
2882template <class _BidirectionalIterator, class _Allocator>
2883 bool
2884 operator!=(const match_results<_BidirectionalIterator, _Allocator>& __x,
2885 const match_results<_BidirectionalIterator, _Allocator>& __y);
2886
2887template <class _BidirectionalIterator, class _Allocator>
2888 void
2889 swap(match_results<_BidirectionalIterator, _Allocator>& __x,
2890 match_results<_BidirectionalIterator, _Allocator>& __y);
2891
2892// regex_search
2893
2894template <class _BidirectionalIterator, class _Allocator, class _CharT, class _Traits>
2895bool
2896regex_search(_BidirectionalIterator __first, _BidirectionalIterator __last,
2897 match_results<_BidirectionalIterator, _Allocator>& __m,
2898 const basic_regex<_CharT, _Traits>& __e,
2899 regex_constants::match_flag_type __flags = regex_constants::match_default);
2900
2901template <class _BidirectionalIterator, class _CharT, class _Traits>
2902inline _LIBCPP_INLINE_VISIBILITY
2903bool
2904regex_search(_BidirectionalIterator __first, _BidirectionalIterator __last,
2905 const basic_regex<_CharT, _Traits>& __e,
2906 regex_constants::match_flag_type __flags = regex_constants::match_default)
2907{
2908 match_results<_BidirectionalIterator> __m;
2909 return _STD::regex_search(__first, __last, __m, __e, __flags);
2910}
2911
2912template <class _CharT, class _Allocator, class _Traits>
2913inline _LIBCPP_INLINE_VISIBILITY
2914bool
2915regex_search(const _CharT* __str, match_results<const _CharT*, _Allocator>& __m,
2916 const basic_regex<_CharT, _Traits>& __e,
2917 regex_constants::match_flag_type __flags = regex_constants::match_default)
2918{
2919 return _STD::regex_search(__str, __str + _Traits::length(__str), __m, __e, __flags);
2920}
2921
2922template <class _CharT, class _Traits>
2923inline _LIBCPP_INLINE_VISIBILITY
2924bool
2925regex_search(const _CharT* __str, const basic_regex<_CharT, _Traits>& __e,
2926 regex_constants::match_flag_type __flags = regex_constants::match_default)
2927{
2928 return _STD::regex_search(__str, __str + _Traits::length(__str), __e, __flags);
2929}
2930
2931template <class _ST, class _SA, class _CharT, class _Traits>
2932inline _LIBCPP_INLINE_VISIBILITY
2933bool
2934regex_search(const basic_string<_CharT, _ST, _SA>& __s,
2935 const basic_regex<_CharT, _Traits>& __e,
2936 regex_constants::match_flag_type __flags = regex_constants::match_default)
2937{
2938 return _STD::regex_search(__s.begin(), __s.end(), __e, __flags);
2939}
2940
2941template <class _ST, class _SA, class _Allocator, class _CharT, class _Traits>
2942inline _LIBCPP_INLINE_VISIBILITY
2943bool
2944regex_search(const basic_string<_CharT, _ST, _SA>& __s,
2945 match_results<typename basic_string<_CharT, _ST, _SA>::const_iterator, _Allocator>& __m,
2946 const basic_regex<_CharT, _Traits>& __e,
2947 regex_constants::match_flag_type __flags = regex_constants::match_default)
2948{
2949 return _STD::regex_search(__s.begin(), __s.end(), __m, __e, __flags);
2950}
2951
2952// regex_match
2953
2954template <class _BidirectionalIterator, class _Allocator, class _CharT, class _Traits>
2955bool
2956regex_match(_BidirectionalIterator __first, _BidirectionalIterator __last,
2957 match_results<_BidirectionalIterator, _Allocator>& __m,
2958 const basic_regex<_CharT, _Traits>& __e,
2959 regex_constants::match_flag_type __flags = regex_constants::match_default)
2960{
2961 bool __r = _STD::regex_search(__first, __last, __m, __e,
2962 __flags | regex_constants::match_continuous);
2963 if (__r)
2964 {
2965 __r = !__m.suffix().matched;
2966 if (!__r)
2967 __m.__matches_.clear();
2968 }
2969 return __r;
2970}
2971
2972template <class _BidirectionalIterator, class _CharT, class _Traits>
2973inline _LIBCPP_INLINE_VISIBILITY
2974bool
2975regex_match(_BidirectionalIterator __first, _BidirectionalIterator __last,
2976 const basic_regex<_CharT, _Traits>& __e,
2977 regex_constants::match_flag_type __flags = regex_constants::match_default)
2978{
2979 match_results<_BidirectionalIterator> __m;
2980 return _STD::regex_match(__first, __last, __m, __e, __flags);
2981}
2982
2983template <class _CharT, class _Allocator, class _Traits>
2984inline _LIBCPP_INLINE_VISIBILITY
2985bool
2986regex_match(const _CharT* __str, match_results<const _CharT*, _Allocator>& __m,
2987 const basic_regex<_CharT, _Traits>& __e,
2988 regex_constants::match_flag_type __flags = regex_constants::match_default)
2989{
2990 return _STD::regex_match(__str, __str + _Traits::length(__str), __m, __e, __flags);
2991}
2992
2993template <class _ST, class _SA, class _Allocator, class _CharT, class _Traits>
2994inline _LIBCPP_INLINE_VISIBILITY
2995bool
2996regex_match(const basic_string<_CharT, _ST, _SA>& __s,
2997 match_results<typename basic_string<_CharT, _ST, _SA>::const_iterator, _Allocator>& __m,
2998 const basic_regex<_CharT, _Traits>& __e,
2999 regex_constants::match_flag_type __flags = regex_constants::match_default)
3000{
3001 return _STD::regex_match(__s.begin(), __s.end(), __m, __e, __flags);
3002}
3003
3004template <class _CharT, class _Traits>
3005inline _LIBCPP_INLINE_VISIBILITY
3006bool
3007regex_match(const _CharT* __str, const basic_regex<_CharT, _Traits>& __e,
3008 regex_constants::match_flag_type __flags = regex_constants::match_default)
3009{
3010 return _STD::regex_match(__str, __str + _Traits::length(__str), __e, __flags);
3011}
3012
3013template <class _ST, class _SA, class _CharT, class _Traits>
3014inline _LIBCPP_INLINE_VISIBILITY
3015bool
3016regex_match(const basic_string<_CharT, _ST, _SA>& __s,
3017 const basic_regex<_CharT, _Traits>& __e,
3018 regex_constants::match_flag_type __flags = regex_constants::match_default)
3019{
3020 return _STD::regex_match(__s.begin(), __s.end(), __e, __flags);
3021}
3022
Howard Hinnant3257c982010-06-17 00:34:59 +00003023_LIBCPP_END_NAMESPACE_STD
3024
3025#endif // _LIBCPP_REGEX