1 #ifndef META_HS_SEMANTIC_HPP 2 #define META_HS_SEMANTIC_HPP 3 4 // Copyright Abel Sinkovics (abel@sinkovics.hu) 2012. 5 // Distributed under the Boost Software License, Version 1.0. 6 // (See accompanying file LICENSE_1_0.txt or copy at 7 // http://www.boost.org/LICENSE_1_0.txt) 8 9 #include <ast.hpp> 10 #include <curry.hpp> 11 12 #include <boost/mpl/if.hpp> 13 #include <boost/mpl/apply_wrap.hpp> 14 #include <boost/mpl/front.hpp> 15 #include <boost/mpl/back.hpp> 16 #include <boost/mpl/at.hpp> 17 #include <boost/mpl/pair.hpp> 18 19 namespace semantic 20 { 21 struct ref 22 { 23 typedef ref type; 24 25 template <class Name> 26 struct apply : ast::ref<Name> {}; 27 }; 28 29 struct value 30 { 31 typedef value type; 32 33 template <class V> 34 struct apply : ast::value<V> {}; 35 }; 36 37 struct lambda 38 { 39 typedef lambda type; 40 41 template <class F, class ArgName> 42 struct apply : ast::lambda<F, ArgName> {}; 43 }; 44 45 struct application 46 { 47 typedef application type; 48 49 template <class F, class Arg> 50 struct apply : ast::application<F, Arg> {}; 51 }; 52 53 class if_ 54 { 55 private: 56 template <class C, class T, class F> 57 struct lazy_if : boost::mpl::if_<typename C::type, T, F> {}; 58 public: 59 typedef if_ type; 60 61 template <class Seq> 62 struct apply : 63 boost::mpl::apply_wrap2< 64 application, 65 typename boost::mpl::apply_wrap2< 66 application, 67 typename boost::mpl::apply_wrap2< 68 application, 69 ast::value<curry3<lazy_if> >, 70 typename boost::mpl::at_c<Seq, 0>::type 71 >::type, 72 typename boost::mpl::at_c<Seq, 1>::type 73 >::type, 74 typename boost::mpl::at_c<Seq, 2>::type 75 > 76 {}; 77 }; 78 79 struct binary_op 80 { 81 typedef binary_op type; 82 83 template <class Exp, class C> 84 struct apply : 85 boost::mpl::apply_wrap2< 86 application, 87 typename boost::mpl::apply_wrap2< 88 application, 89 typename boost::mpl::apply_wrap1< 90 ref, 91 typename boost::mpl::front<C>::type 92 >::type, 93 Exp 94 >::type, 95 typename boost::mpl::back<C>::type 96 > 97 {}; 98 }; 99 100 struct pair 101 { 102 typedef pair type; 103 104 template <class Seq> 105 struct apply : 106 boost::mpl::pair< 107 typename boost::mpl::front<Seq>::type, 108 ast::top_bound<typename boost::mpl::back<Seq>::type> 109 > 110 {}; 111 }; 112 } 113 114 #endif 115 116