* include/bits/regex_compiler.h (__detail::_AnyMatcher,
[official-gcc.git] / libstdc++-v3 / include / bits / regex_compiler.h
blob406d9a9fd6b118f547d572af6323d1a4f8813ffe
1 // class template regex -*- C++ -*-
3 // Copyright (C) 2010-2013 Free Software Foundation, Inc.
4 //
5 // This file is part of the GNU ISO C++ Library. This library is free
6 // software; you can redistribute it and/or modify it under the
7 // terms of the GNU General Public License as published by the
8 // Free Software Foundation; either version 3, or (at your option)
9 // any later version.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
16 // Under Section 7 of GPL version 3, you are granted additional
17 // permissions described in the GCC Runtime Library Exception, version
18 // 3.1, as published by the Free Software Foundation.
20 // You should have received a copy of the GNU General Public License and
21 // a copy of the GCC Runtime Library Exception along with this program;
22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23 // <http://www.gnu.org/licenses/>.
25 /**
26 * @file bits/regex_compiler.h
27 * This is an internal header file, included by other library headers.
28 * Do not attempt to use it directly. @headername{regex}
31 namespace std _GLIBCXX_VISIBILITY(default)
33 namespace __detail
35 _GLIBCXX_BEGIN_NAMESPACE_VERSION
37 /**
38 * @addtogroup regex-detail
39 * @{
42 template<typename _TraitsT>
43 struct _BracketMatcher;
45 /// Builds an NFA from an input iterator interval.
46 template<typename _FwdIter, typename _TraitsT>
47 class _Compiler
49 public:
50 typedef typename _TraitsT::string_type _StringT;
51 typedef _NFA<_TraitsT> _RegexT;
52 typedef regex_constants::syntax_option_type _FlagT;
54 _Compiler(_FwdIter __b, _FwdIter __e,
55 const _TraitsT& __traits, _FlagT __flags);
57 std::shared_ptr<_RegexT>
58 _M_get_nfa()
59 { return make_shared<_RegexT>(std::move(_M_nfa)); }
61 private:
62 typedef _Scanner<_FwdIter> _ScannerT;
63 typedef typename _ScannerT::_TokenT _TokenT;
64 typedef _StateSeq<_TraitsT> _StateSeqT;
65 typedef std::stack<_StateSeqT, std::vector<_StateSeqT>> _StackT;
66 typedef _BracketMatcher<_TraitsT> _BMatcherT;
67 typedef std::ctype<typename _TraitsT::char_type> _CtypeT;
69 // accepts a specific token or returns false.
70 bool
71 _M_match_token(_TokenT __token);
73 void
74 _M_disjunction();
76 void
77 _M_alternative();
79 bool
80 _M_term();
82 bool
83 _M_assertion();
85 void
86 _M_quantifier();
88 bool
89 _M_atom();
91 bool
92 _M_bracket_expression();
94 void
95 _M_expression_term(_BMatcherT& __matcher);
97 bool
98 _M_range_expression(_BMatcherT& __matcher);
100 bool
101 _M_collating_symbol(_BMatcherT& __matcher);
103 bool
104 _M_equivalence_class(_BMatcherT& __matcher);
106 bool
107 _M_character_class(_BMatcherT& __matcher);
110 _M_cur_int_value(int __radix);
112 bool
113 _M_try_char();
115 _StateSeqT
116 _M_pop()
118 auto ret = _M_stack.top();
119 _M_stack.pop();
120 return ret;
123 _FlagT _M_flags;
124 const _TraitsT& _M_traits;
125 const _CtypeT& _M_ctype;
126 _ScannerT _M_scanner;
127 _RegexT _M_nfa;
128 _StringT _M_value;
129 _StackT _M_stack;
132 template<typename _FwdIter, typename _TraitsT>
133 inline std::shared_ptr<_NFA<_TraitsT>>
134 __compile_nfa(_FwdIter __first, _FwdIter __last, const _TraitsT& __traits,
135 regex_constants::syntax_option_type __flags)
137 using _Cmplr = _Compiler<_FwdIter, _TraitsT>;
138 return _Cmplr(__first, __last, __traits, __flags)._M_get_nfa();
141 template<typename _TraitsT>
142 struct _AnyMatcher
144 typedef typename _TraitsT::char_type _CharT;
146 explicit
147 _AnyMatcher(const _TraitsT& __traits)
148 : _M_traits(__traits)
151 bool
152 operator()(_CharT __ch) const
154 return _M_traits.translate(__ch) != '\n'
155 && _M_traits.translate(__ch) != '\r'
156 && _M_traits.translate(__ch) != u'\u2028'
157 && _M_traits.translate(__ch) != u'\u2029';
160 const _TraitsT& _M_traits;
163 template<typename _TraitsT>
164 struct _CharMatcher
166 typedef typename _TraitsT::char_type _CharT;
167 typedef regex_constants::syntax_option_type _FlagT;
169 explicit
170 _CharMatcher(_CharT __ch, const _TraitsT& __traits, _FlagT __flags)
171 : _M_traits(__traits), _M_flags(__flags), _M_ch(_M_translate(__ch))
174 bool
175 operator()(_CharT __ch) const
176 { return _M_ch == _M_translate(__ch); }
178 _CharT
179 _M_translate(_CharT __ch) const
181 if (_M_flags & regex_constants::icase)
182 return _M_traits.translate_nocase(__ch);
183 else
184 return _M_traits.translate(__ch);
187 const _TraitsT& _M_traits;
188 _FlagT _M_flags;
189 _CharT _M_ch;
192 /// Matches a character range (bracket expression)
193 template<typename _TraitsT>
194 struct _BracketMatcher
196 typedef typename _TraitsT::char_type _CharT;
197 typedef typename _TraitsT::char_class_type _CharClassT;
198 typedef typename _TraitsT::string_type _StringT;
199 typedef regex_constants::syntax_option_type _FlagT;
201 explicit
202 _BracketMatcher(bool __is_non_matching,
203 const _TraitsT& __traits,
204 _FlagT __flags)
205 : _M_traits(__traits), _M_class_set(0), _M_flags(__flags),
206 _M_is_non_matching(__is_non_matching)
209 bool
210 operator()(_CharT) const;
212 void
213 _M_add_char(_CharT __c)
214 { _M_char_set.insert(_M_translate(__c)); }
216 void
217 _M_add_collating_element(const _StringT& __s)
219 auto __st = _M_traits.lookup_collatename(__s.data(),
220 __s.data() + __s.size());
221 if (__st.empty())
222 __throw_regex_error(regex_constants::error_collate);
223 _M_char_set.insert(_M_translate(__st[0]));
226 void
227 _M_add_equivalence_class(const _StringT& __s)
229 auto __st = _M_traits.lookup_collatename(__s.data(),
230 __s.data() + __s.size());
231 if (__st.empty())
232 __throw_regex_error(regex_constants::error_collate);
233 __st = _M_traits.transform_primary(__st.data(),
234 __st.data() + __st.size());
235 _M_equiv_set.insert(__st);
238 void
239 _M_add_character_class(const _StringT& __s)
241 auto __mask = _M_traits.lookup_classname(__s.data(),
242 __s.data() + __s.size(),
243 _M_is_icase());
244 if (__mask == 0)
245 __throw_regex_error(regex_constants::error_ctype);
246 _M_class_set |= __mask;
249 void
250 _M_make_range(_CharT __l, _CharT __r)
252 if (_M_flags & regex_constants::collate)
253 _M_range_set.insert(
254 make_pair(_M_get_str(_M_translate(__l)),
255 _M_get_str(_M_translate(__r))));
256 else
257 _M_range_set.insert(make_pair(_M_get_str(__l), _M_get_str(__r)));
260 _CharT
261 _M_translate(_CharT __c) const
263 if (_M_is_icase())
264 return _M_traits.translate_nocase(__c);
265 else
266 return _M_traits.translate(__c);
269 bool
270 _M_is_icase() const
271 { return _M_flags & regex_constants::icase; }
273 _StringT
274 _M_get_str(_CharT __c) const
276 _StringT __s(1, __c);
277 return _M_traits.transform(__s.begin(), __s.end());
280 std::set<_CharT> _M_char_set;
281 std::set<_StringT> _M_equiv_set;
282 std::set<pair<_StringT, _StringT>> _M_range_set;
283 const _TraitsT& _M_traits;
284 _CharClassT _M_class_set;
285 _FlagT _M_flags;
286 bool _M_is_non_matching;
289 //@} regex-detail
290 _GLIBCXX_END_NAMESPACE_VERSION
291 } // namespace __detail
292 } // namespace std
294 #include <bits/regex_compiler.tcc>