RequirementChecker.h
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041 #ifndef _RequirementChecker_h_
00042 #define _RequirementChecker_h_
00043
00044 #include "boost/mpl/begin.hpp"
00045 #include "boost/mpl/end.hpp"
00046 #include "boost/mpl/deref.hpp"
00047 #include "boost/mpl/next.hpp"
00048 #include "boost/mpl/eval_if.hpp"
00049 #include "boost/mpl/integral_c.hpp"
00050 #include "boost/mpl/bool.hpp"
00051
00052 #include "boost/mpl/filter_view.hpp"
00053
00054 #include "mw/attributes/type_traits/is_null.h"
00055 #include "mw/attributes/detail/AttributeCompileErrors.h"
00056
00057 namespace famouso {
00058 namespace mw {
00059 namespace attributes {
00060 namespace detail {
00061
00066 struct RequirablePred {
00067 template <typename Attr>
00068 struct apply : boost::mpl::bool_<Attr::requirable> {};
00069 };
00070
00088 template <typename Prov, typename Req, bool compileError = true,
00089 typename FilteredReq = typename boost::mpl::filter_view<
00090 typename Req::sequence,
00091 RequirablePred
00092 >::type,
00093 typename ReqIter = typename boost::mpl::begin<FilteredReq>::type
00094 >
00095 struct RequirementChecker {
00096 private:
00097
00098
00099 template <typename Pr, typename PrIter = typename boost::mpl::begin<Pr>::type>
00100 struct provision_assertion {
00101 private:
00102 typedef typename boost::mpl::deref<PrIter>::type curProvAttr;
00103
00104 FAMOUSO_STATIC_ASSERT_ERROR(
00105 (curProvAttr::requirable),
00106 provision_contains_non_requirable_attribute,
00107 (curProvAttr, Pr));
00108
00109 public:
00110 typedef typename provision_assertion<
00111 Pr,
00112 typename boost::mpl::next<PrIter>::type
00113 >::type type;
00114 };
00115 template <typename Pr>
00116 struct provision_assertion<Pr, typename boost::mpl::end<Pr>::type> {
00117 typedef provision_assertion type;
00118 };
00119
00120 typedef typename provision_assertion<
00121 typename Prov::sequence
00122 >::type assertProvision;
00123
00128 typedef typename boost::mpl::deref<ReqIter>::type curAttr;
00129
00134 typedef typename Prov::template find_ct<curAttr>::type provAttr;
00135
00140 typedef famouso::mw::attributes::type_traits::is_null<
00141 provAttr
00142 > notContained;
00143
00152 template <typename Attribute, bool dummy>
00153 struct comparatorExtractor {
00154 typedef typename Attribute::template isStronger<curAttr> compare;
00155 };
00156 template <bool dummy>
00157 struct comparatorExtractor<famouso::mw::attributes::Null, dummy> {
00158
00159
00160 typedef boost::mpl::bool_<true> compare;
00161 };
00162
00167 static const bool valueFits = comparatorExtractor<provAttr, false>::compare::value;
00168
00169 typedef typename AttributeIsNotRequireable<
00170 curAttr::requirable, curAttr, Req, compileError
00171 >::type assert1;
00172
00173
00174
00175 static const bool issueNotContainedError = (notContained::value && curAttr::requirable);
00176
00181 typedef typename RequiredAttributeNotContainedInProvision<
00182 !issueNotContainedError , curAttr, Prov, compileError
00183 >::type assert2;
00184
00189 typedef typename RequiredValueNotProvided<
00190 valueFits, curAttr, provAttr, compileError
00191 >::type assert3;
00192
00197 typedef typename RequirementChecker<
00198 Prov,
00199 Req,
00200 compileError,
00201 FilteredReq,
00202 typename boost::mpl::next<ReqIter>::type
00203 >::result nextResult;
00204 public:
00208 typedef RequirementChecker type;
00209
00210 typedef boost::mpl::integral_c_tag tag;
00211
00212 typedef bool value_type;
00213
00214 typedef typename boost::mpl::eval_if_c<
00215 (!notContained::value && valueFits),
00216 nextResult,
00217 boost::mpl::bool_<false>
00218 >::type result;
00219
00228 static const bool value = result::value;
00229
00230 operator bool() const {
00231 return (this->value);
00232 }
00233 };
00234
00235 template <typename Prov, typename Req, typename FilteredReq>
00236 struct RequirementChecker<
00237 Prov,
00238 Req,
00239 true,
00240 FilteredReq,
00241 typename boost::mpl::end<FilteredReq>::type
00242 > : public boost::mpl::integral_c<bool, true> {
00243 public:
00244 typedef RequirementChecker type;
00245
00246 typedef boost::mpl::bool_<true> result;
00247 };
00248
00249 template <typename Prov, typename Req, typename FilteredReq>
00250 struct RequirementChecker<
00251 Prov,
00252 Req,
00253 false,
00254 FilteredReq,
00255 typename boost::mpl::end<FilteredReq>::type
00256 > : public boost::mpl::integral_c<bool, true> {
00257 public:
00258 typedef RequirementChecker type;
00259
00260 typedef boost::mpl::bool_<true> result;
00261 };
00262
00263 }
00264 }
00265 }
00266 }
00267
00268 #endif