1 /*============================================================================= 2 Copyright (c) 2009 Hartmut Kaiser 3 Copyright (c) 2014 Joel de Guzman 4 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 #ifndef BOOST_SPIRIT_X3_NUMERIC_BOOL_HPP 9 #define BOOST_SPIRIT_X3_NUMERIC_BOOL_HPP 10 11 #include <boost/spirit/home/x3/core/parser.hpp> 12 #include <boost/spirit/home/x3/core/skip_over.hpp> 13 #include <boost/spirit/home/x3/numeric/bool_policies.hpp> 14 15 namespace boost { namespace spirit { namespace x3 16 { 17 template <typename T, typename Encoding, typename BoolPolicies = bool_policies<T>> 18 struct bool_parser : parser<bool_parser<T, Encoding, BoolPolicies>> 19 { 20 typedef Encoding encoding; 21 typedef T attribute_type; 22 static bool const has_attribute = true; 23 bool_parserboost::spirit::x3::bool_parser24 constexpr bool_parser() 25 : policies() {} 26 bool_parserboost::spirit::x3::bool_parser27 constexpr bool_parser(BoolPolicies const& policies) 28 : policies(policies) {} 29 30 template <typename Iterator, typename Context> parseboost::spirit::x3::bool_parser31 bool parse(Iterator& first, Iterator const& last 32 , Context const& context, unused_type, T& attr) const 33 { 34 x3::skip_over(first, last, context); 35 return policies.parse_true(first, last, attr, get_case_compare<encoding>(context)) 36 || policies.parse_false(first, last, attr, get_case_compare<encoding>(context)); 37 } 38 39 template <typename Iterator, typename Context, typename Attribute> parseboost::spirit::x3::bool_parser40 bool parse(Iterator& first, Iterator const& last 41 , Context const& context, unused_type, Attribute& attr_param) const 42 { 43 // this case is called when Attribute is not T 44 T attr_; 45 if (parse(first, last, context, unused, attr_)) 46 { 47 traits::move_to(attr_, attr_param); 48 return true; 49 } 50 return false; 51 } 52 53 BoolPolicies policies; 54 }; 55 56 template <typename T, typename Encoding, typename BoolPolicies = bool_policies<T>> 57 struct literal_bool_parser : parser<bool_parser<T, Encoding, BoolPolicies>> 58 { 59 typedef Encoding encoding; 60 typedef T attribute_type; 61 static bool const has_attribute = true; 62 63 template <typename Value> literal_bool_parserboost::spirit::x3::literal_bool_parser64 constexpr literal_bool_parser(Value const& n) 65 : policies(), n_(n) {} 66 67 template <typename Value> literal_bool_parserboost::spirit::x3::literal_bool_parser68 constexpr literal_bool_parser(Value const& n, BoolPolicies const& policies) 69 : policies(policies), n_(n) {} 70 71 template <typename Iterator, typename Context> parse_mainboost::spirit::x3::literal_bool_parser72 bool parse_main(Iterator& first, Iterator const& last 73 , Context const& context, T& attr) const 74 { 75 x3::skip_over(first, last, context); 76 return (n_ && policies.parse_true(first, last, attr, get_case_compare<encoding>(context))) 77 || (!n_ && policies.parse_false(first, last, attr, get_case_compare<encoding>(context))); 78 } 79 80 template <typename Iterator, typename Context> parseboost::spirit::x3::literal_bool_parser81 bool parse(Iterator& first, Iterator const& last 82 , Context const& context, unused_type, T& attr) const 83 { 84 return parse_main(first, last, context, attr); 85 } 86 87 template <typename Iterator, typename Context, typename Attribute> parseboost::spirit::x3::literal_bool_parser88 bool parse(Iterator& first, Iterator const& last 89 , Context const& context, unused_type, Attribute& attr_param) const 90 { 91 // this case is called when Attribute is not T 92 T attr_; 93 if (parse_main(first, last, context, attr_)) 94 { 95 traits::move_to(attr_, attr_param); 96 return true; 97 } 98 return false; 99 } 100 101 BoolPolicies policies; 102 T n_; 103 }; 104 105 namespace standard 106 { 107 typedef bool_parser<bool, char_encoding::standard> bool_type; 108 constexpr bool_type bool_ = {}; 109 110 typedef literal_bool_parser<bool, char_encoding::standard> true_type; 111 constexpr true_type true_ = { true }; 112 113 typedef literal_bool_parser<bool, char_encoding::standard> false_type; 114 constexpr false_type false_ = { false }; 115 } 116 117 #ifndef BOOST_SPIRIT_NO_STANDARD_WIDE 118 namespace standard_wide 119 { 120 typedef bool_parser<bool, char_encoding::standard_wide> bool_type; 121 constexpr bool_type bool_ = {}; 122 123 typedef literal_bool_parser<bool, char_encoding::standard_wide> true_type; 124 constexpr true_type true_ = { true }; 125 126 typedef literal_bool_parser<bool, char_encoding::standard_wide> false_type; 127 constexpr false_type false_ = { false }; 128 } 129 #endif 130 131 namespace ascii 132 { 133 typedef bool_parser<bool, char_encoding::ascii> bool_type; 134 constexpr bool_type bool_ = {}; 135 136 typedef literal_bool_parser<bool, char_encoding::ascii> true_type; 137 constexpr true_type true_ = { true }; 138 139 typedef literal_bool_parser<bool, char_encoding::ascii> false_type; 140 constexpr false_type false_ = { false }; 141 } 142 143 namespace iso8859_1 144 { 145 typedef bool_parser<bool, char_encoding::iso8859_1> bool_type; 146 constexpr bool_type bool_ = {}; 147 148 typedef literal_bool_parser<bool, char_encoding::iso8859_1> true_type; 149 constexpr true_type true_ = { true }; 150 151 typedef literal_bool_parser<bool, char_encoding::iso8859_1> false_type; 152 constexpr false_type false_ = { false }; 153 } 154 155 using standard::bool_; 156 using standard::true_; 157 using standard::false_; 158 159 }}} 160 161 #endif 162