/Src/Dependencies/Boost/boost/spirit/home/classic/core/primitives/primitives.hpp

http://hadesmem.googlecode.com/ · C++ Header · 654 lines · 411 code · 115 blank · 128 comment · 13 complexity · 61cf4e39f2be99f7144b58848fab49cc MD5 · raw file

  1. /*=============================================================================
  2. Copyright (c) 1998-2003 Joel de Guzman
  3. Copyright (c) 2003 Martin Wille
  4. http://spirit.sourceforge.net/
  5. Distributed under the Boost Software License, Version 1.0. (See accompanying
  6. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  7. =============================================================================*/
  8. #if !defined(BOOST_SPIRIT_PRIMITIVES_HPP)
  9. #define BOOST_SPIRIT_PRIMITIVES_HPP
  10. #include <boost/ref.hpp>
  11. #include <boost/spirit/home/classic/namespace.hpp>
  12. #include <boost/spirit/home/classic/core/assert.hpp>
  13. #include <boost/spirit/home/classic/core/parser.hpp>
  14. #include <boost/spirit/home/classic/core/composite/impl/directives.ipp>
  15. #include <boost/spirit/home/classic/core/primitives/impl/primitives.ipp>
  16. #ifdef BOOST_MSVC
  17. #pragma warning (push)
  18. #pragma warning(disable : 4512)
  19. #endif
  20. namespace boost { namespace spirit {
  21. BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
  22. ///////////////////////////////////////////////////////////////////////////
  23. //
  24. // char_parser class
  25. //
  26. ///////////////////////////////////////////////////////////////////////////
  27. template <typename DerivedT>
  28. struct char_parser : public parser<DerivedT>
  29. {
  30. typedef DerivedT self_t;
  31. template <typename ScannerT>
  32. struct result
  33. {
  34. typedef typename match_result<
  35. ScannerT,
  36. typename ScannerT::value_t
  37. >::type type;
  38. };
  39. template <typename ScannerT>
  40. typename parser_result<self_t, ScannerT>::type
  41. parse(ScannerT const& scan) const
  42. {
  43. typedef typename parser_result<self_t, ScannerT>::type result_t;
  44. typedef typename ScannerT::value_t value_t;
  45. typedef typename ScannerT::iterator_t iterator_t;
  46. if (!scan.at_end())
  47. {
  48. value_t ch = *scan;
  49. if (this->derived().test(ch))
  50. {
  51. iterator_t save(scan.first);
  52. ++scan.first;
  53. return scan.create_match(1, ch, save, scan.first);
  54. }
  55. }
  56. return scan.no_match();
  57. }
  58. };
  59. ///////////////////////////////////////////////////////////////////////////
  60. //
  61. // negation of char_parsers
  62. //
  63. ///////////////////////////////////////////////////////////////////////////
  64. template <typename PositiveT>
  65. struct negated_char_parser
  66. : public char_parser<negated_char_parser<PositiveT> >
  67. {
  68. typedef negated_char_parser<PositiveT> self_t;
  69. typedef PositiveT positive_t;
  70. negated_char_parser(positive_t const& p)
  71. : positive(p.derived()) {}
  72. template <typename T>
  73. bool test(T ch) const
  74. {
  75. return !positive.test(ch);
  76. }
  77. positive_t const positive;
  78. };
  79. template <typename ParserT>
  80. inline negated_char_parser<ParserT>
  81. operator~(char_parser<ParserT> const& p)
  82. {
  83. return negated_char_parser<ParserT>(p.derived());
  84. }
  85. template <typename ParserT>
  86. inline ParserT
  87. operator~(negated_char_parser<ParserT> const& n)
  88. {
  89. return n.positive;
  90. }
  91. ///////////////////////////////////////////////////////////////////////////
  92. //
  93. // chlit class
  94. //
  95. ///////////////////////////////////////////////////////////////////////////
  96. template <typename CharT = char>
  97. struct chlit : public char_parser<chlit<CharT> >
  98. {
  99. chlit(CharT ch_)
  100. : ch(ch_) {}
  101. template <typename T>
  102. bool test(T ch_) const
  103. {
  104. return ch_ == ch;
  105. }
  106. CharT ch;
  107. };
  108. template <typename CharT>
  109. inline chlit<CharT>
  110. ch_p(CharT ch)
  111. {
  112. return chlit<CharT>(ch);
  113. }
  114. // This should take care of ch_p("a") "bugs"
  115. template <typename CharT, std::size_t N>
  116. inline chlit<CharT>
  117. ch_p(CharT const (& str)[N])
  118. {
  119. // ch_p's argument should be a single character or a null-terminated
  120. // string with a single character
  121. BOOST_STATIC_ASSERT(N < 3);
  122. return chlit<CharT>(str[0]);
  123. }
  124. ///////////////////////////////////////////////////////////////////////////
  125. //
  126. // range class
  127. //
  128. ///////////////////////////////////////////////////////////////////////////
  129. template <typename CharT = char>
  130. struct range : public char_parser<range<CharT> >
  131. {
  132. range(CharT first_, CharT last_)
  133. : first(first_), last(last_)
  134. {
  135. BOOST_SPIRIT_ASSERT(!(last < first));
  136. }
  137. template <typename T>
  138. bool test(T ch) const
  139. {
  140. return !(CharT(ch) < first) && !(last < CharT(ch));
  141. }
  142. CharT first;
  143. CharT last;
  144. };
  145. template <typename CharT>
  146. inline range<CharT>
  147. range_p(CharT first, CharT last)
  148. {
  149. return range<CharT>(first, last);
  150. }
  151. ///////////////////////////////////////////////////////////////////////////
  152. //
  153. // chseq class
  154. //
  155. ///////////////////////////////////////////////////////////////////////////
  156. template <typename IteratorT = char const*>
  157. class chseq : public parser<chseq<IteratorT> >
  158. {
  159. public:
  160. typedef chseq<IteratorT> self_t;
  161. chseq(IteratorT first_, IteratorT last_)
  162. : first(first_), last(last_) {}
  163. chseq(IteratorT first_)
  164. : first(first_), last(impl::get_last(first_)) {}
  165. template <typename ScannerT>
  166. typename parser_result<self_t, ScannerT>::type
  167. parse(ScannerT const& scan) const
  168. {
  169. typedef typename boost::unwrap_reference<IteratorT>::type striter_t;
  170. typedef typename parser_result<self_t, ScannerT>::type result_t;
  171. return impl::string_parser_parse<result_t>(
  172. striter_t(first),
  173. striter_t(last),
  174. scan);
  175. }
  176. private:
  177. IteratorT first;
  178. IteratorT last;
  179. };
  180. template <typename CharT>
  181. inline chseq<CharT const*>
  182. chseq_p(CharT const* str)
  183. {
  184. return chseq<CharT const*>(str);
  185. }
  186. template <typename IteratorT>
  187. inline chseq<IteratorT>
  188. chseq_p(IteratorT first, IteratorT last)
  189. {
  190. return chseq<IteratorT>(first, last);
  191. }
  192. ///////////////////////////////////////////////////////////////////////////
  193. //
  194. // strlit class
  195. //
  196. ///////////////////////////////////////////////////////////////////////////
  197. template <typename IteratorT = char const*>
  198. class strlit : public parser<strlit<IteratorT> >
  199. {
  200. public:
  201. typedef strlit<IteratorT> self_t;
  202. strlit(IteratorT first, IteratorT last)
  203. : seq(first, last) {}
  204. strlit(IteratorT first)
  205. : seq(first) {}
  206. template <typename ScannerT>
  207. typename parser_result<self_t, ScannerT>::type
  208. parse(ScannerT const& scan) const
  209. {
  210. typedef typename parser_result<self_t, ScannerT>::type result_t;
  211. return impl::contiguous_parser_parse<result_t>
  212. (seq, scan, scan);
  213. }
  214. private:
  215. chseq<IteratorT> seq;
  216. };
  217. template <typename CharT>
  218. inline strlit<CharT const*>
  219. str_p(CharT const* str)
  220. {
  221. return strlit<CharT const*>(str);
  222. }
  223. template <typename CharT>
  224. inline strlit<CharT *>
  225. str_p(CharT * str)
  226. {
  227. return strlit<CharT *>(str);
  228. }
  229. template <typename IteratorT>
  230. inline strlit<IteratorT>
  231. str_p(IteratorT first, IteratorT last)
  232. {
  233. return strlit<IteratorT>(first, last);
  234. }
  235. // This should take care of str_p('a') "bugs"
  236. template <typename CharT>
  237. inline chlit<CharT>
  238. str_p(CharT ch)
  239. {
  240. return chlit<CharT>(ch);
  241. }
  242. ///////////////////////////////////////////////////////////////////////////
  243. //
  244. // nothing_parser class
  245. //
  246. ///////////////////////////////////////////////////////////////////////////
  247. struct nothing_parser : public parser<nothing_parser>
  248. {
  249. typedef nothing_parser self_t;
  250. nothing_parser() {}
  251. template <typename ScannerT>
  252. typename parser_result<self_t, ScannerT>::type
  253. parse(ScannerT const& scan) const
  254. {
  255. return scan.no_match();
  256. }
  257. };
  258. nothing_parser const nothing_p = nothing_parser();
  259. ///////////////////////////////////////////////////////////////////////////
  260. //
  261. // anychar_parser class
  262. //
  263. ///////////////////////////////////////////////////////////////////////////
  264. struct anychar_parser : public char_parser<anychar_parser>
  265. {
  266. typedef anychar_parser self_t;
  267. anychar_parser() {}
  268. template <typename CharT>
  269. bool test(CharT) const
  270. {
  271. return true;
  272. }
  273. };
  274. anychar_parser const anychar_p = anychar_parser();
  275. inline nothing_parser
  276. operator~(anychar_parser)
  277. {
  278. return nothing_p;
  279. }
  280. ///////////////////////////////////////////////////////////////////////////
  281. //
  282. // alnum_parser class
  283. //
  284. ///////////////////////////////////////////////////////////////////////////
  285. struct alnum_parser : public char_parser<alnum_parser>
  286. {
  287. typedef alnum_parser self_t;
  288. alnum_parser() {}
  289. template <typename CharT>
  290. bool test(CharT ch) const
  291. {
  292. return impl::isalnum_(ch);
  293. }
  294. };
  295. alnum_parser const alnum_p = alnum_parser();
  296. ///////////////////////////////////////////////////////////////////////////
  297. //
  298. // alpha_parser class
  299. //
  300. ///////////////////////////////////////////////////////////////////////////
  301. struct alpha_parser : public char_parser<alpha_parser>
  302. {
  303. typedef alpha_parser self_t;
  304. alpha_parser() {}
  305. template <typename CharT>
  306. bool test(CharT ch) const
  307. {
  308. return impl::isalpha_(ch);
  309. }
  310. };
  311. alpha_parser const alpha_p = alpha_parser();
  312. ///////////////////////////////////////////////////////////////////////////
  313. //
  314. // cntrl_parser class
  315. //
  316. ///////////////////////////////////////////////////////////////////////////
  317. struct cntrl_parser : public char_parser<cntrl_parser>
  318. {
  319. typedef cntrl_parser self_t;
  320. cntrl_parser() {}
  321. template <typename CharT>
  322. bool test(CharT ch) const
  323. {
  324. return impl::iscntrl_(ch);
  325. }
  326. };
  327. cntrl_parser const cntrl_p = cntrl_parser();
  328. ///////////////////////////////////////////////////////////////////////////
  329. //
  330. // digit_parser class
  331. //
  332. ///////////////////////////////////////////////////////////////////////////
  333. struct digit_parser : public char_parser<digit_parser>
  334. {
  335. typedef digit_parser self_t;
  336. digit_parser() {}
  337. template <typename CharT>
  338. bool test(CharT ch) const
  339. {
  340. return impl::isdigit_(ch);
  341. }
  342. };
  343. digit_parser const digit_p = digit_parser();
  344. ///////////////////////////////////////////////////////////////////////////
  345. //
  346. // graph_parser class
  347. //
  348. ///////////////////////////////////////////////////////////////////////////
  349. struct graph_parser : public char_parser<graph_parser>
  350. {
  351. typedef graph_parser self_t;
  352. graph_parser() {}
  353. template <typename CharT>
  354. bool test(CharT ch) const
  355. {
  356. return impl::isgraph_(ch);
  357. }
  358. };
  359. graph_parser const graph_p = graph_parser();
  360. ///////////////////////////////////////////////////////////////////////////
  361. //
  362. // lower_parser class
  363. //
  364. ///////////////////////////////////////////////////////////////////////////
  365. struct lower_parser : public char_parser<lower_parser>
  366. {
  367. typedef lower_parser self_t;
  368. lower_parser() {}
  369. template <typename CharT>
  370. bool test(CharT ch) const
  371. {
  372. return impl::islower_(ch);
  373. }
  374. };
  375. lower_parser const lower_p = lower_parser();
  376. ///////////////////////////////////////////////////////////////////////////
  377. //
  378. // print_parser class
  379. //
  380. ///////////////////////////////////////////////////////////////////////////
  381. struct print_parser : public char_parser<print_parser>
  382. {
  383. typedef print_parser self_t;
  384. print_parser() {}
  385. template <typename CharT>
  386. bool test(CharT ch) const
  387. {
  388. return impl::isprint_(ch);
  389. }
  390. };
  391. print_parser const print_p = print_parser();
  392. ///////////////////////////////////////////////////////////////////////////
  393. //
  394. // punct_parser class
  395. //
  396. ///////////////////////////////////////////////////////////////////////////
  397. struct punct_parser : public char_parser<punct_parser>
  398. {
  399. typedef punct_parser self_t;
  400. punct_parser() {}
  401. template <typename CharT>
  402. bool test(CharT ch) const
  403. {
  404. return impl::ispunct_(ch);
  405. }
  406. };
  407. punct_parser const punct_p = punct_parser();
  408. ///////////////////////////////////////////////////////////////////////////
  409. //
  410. // blank_parser class
  411. //
  412. ///////////////////////////////////////////////////////////////////////////
  413. struct blank_parser : public char_parser<blank_parser>
  414. {
  415. typedef blank_parser self_t;
  416. blank_parser() {}
  417. template <typename CharT>
  418. bool test(CharT ch) const
  419. {
  420. return impl::isblank_(ch);
  421. }
  422. };
  423. blank_parser const blank_p = blank_parser();
  424. ///////////////////////////////////////////////////////////////////////////
  425. //
  426. // space_parser class
  427. //
  428. ///////////////////////////////////////////////////////////////////////////
  429. struct space_parser : public char_parser<space_parser>
  430. {
  431. typedef space_parser self_t;
  432. space_parser() {}
  433. template <typename CharT>
  434. bool test(CharT ch) const
  435. {
  436. return impl::isspace_(ch);
  437. }
  438. };
  439. space_parser const space_p = space_parser();
  440. ///////////////////////////////////////////////////////////////////////////
  441. //
  442. // upper_parser class
  443. //
  444. ///////////////////////////////////////////////////////////////////////////
  445. struct upper_parser : public char_parser<upper_parser>
  446. {
  447. typedef upper_parser self_t;
  448. upper_parser() {}
  449. template <typename CharT>
  450. bool test(CharT ch) const
  451. {
  452. return impl::isupper_(ch);
  453. }
  454. };
  455. upper_parser const upper_p = upper_parser();
  456. ///////////////////////////////////////////////////////////////////////////
  457. //
  458. // xdigit_parser class
  459. //
  460. ///////////////////////////////////////////////////////////////////////////
  461. struct xdigit_parser : public char_parser<xdigit_parser>
  462. {
  463. typedef xdigit_parser self_t;
  464. xdigit_parser() {}
  465. template <typename CharT>
  466. bool test(CharT ch) const
  467. {
  468. return impl::isxdigit_(ch);
  469. }
  470. };
  471. xdigit_parser const xdigit_p = xdigit_parser();
  472. ///////////////////////////////////////////////////////////////////////////
  473. //
  474. // eol_parser class (contributed by Martin Wille)
  475. //
  476. ///////////////////////////////////////////////////////////////////////////
  477. struct eol_parser : public parser<eol_parser>
  478. {
  479. typedef eol_parser self_t;
  480. eol_parser() {}
  481. template <typename ScannerT>
  482. typename parser_result<self_t, ScannerT>::type
  483. parse(ScannerT const& scan) const
  484. {
  485. typename ScannerT::iterator_t save = scan.first;
  486. std::size_t len = 0;
  487. if (!scan.at_end() && *scan == '\r') // CR
  488. {
  489. ++scan.first;
  490. ++len;
  491. }
  492. // Don't call skipper here
  493. if (scan.first != scan.last && *scan == '\n') // LF
  494. {
  495. ++scan.first;
  496. ++len;
  497. }
  498. if (len)
  499. return scan.create_match(len, nil_t(), save, scan.first);
  500. return scan.no_match();
  501. }
  502. };
  503. eol_parser const eol_p = eol_parser();
  504. ///////////////////////////////////////////////////////////////////////////
  505. //
  506. // end_parser class (suggested by Markus Schoepflin)
  507. //
  508. ///////////////////////////////////////////////////////////////////////////
  509. struct end_parser : public parser<end_parser>
  510. {
  511. typedef end_parser self_t;
  512. end_parser() {}
  513. template <typename ScannerT>
  514. typename parser_result<self_t, ScannerT>::type
  515. parse(ScannerT const& scan) const
  516. {
  517. if (scan.at_end())
  518. return scan.empty_match();
  519. return scan.no_match();
  520. }
  521. };
  522. end_parser const end_p = end_parser();
  523. ///////////////////////////////////////////////////////////////////////////
  524. //
  525. // the pizza_p parser :-)
  526. //
  527. ///////////////////////////////////////////////////////////////////////////
  528. inline strlit<char const*> const
  529. pizza_p(char const* your_favorite_pizza)
  530. {
  531. return your_favorite_pizza;
  532. }
  533. BOOST_SPIRIT_CLASSIC_NAMESPACE_END
  534. }} // namespace BOOST_SPIRIT_CLASSIC_NS
  535. #ifdef BOOST_MSVC
  536. #pragma warning (pop)
  537. #endif
  538. #endif