Chris@16: // Copyright Daniel Wallin 2006. Use, modification and distribution is Chris@16: // subject to the Boost Software License, Version 1.0. (See accompanying Chris@16: // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) Chris@16: Chris@16: // Chris@16: // 2009.10.21 TDS remove depenency on boost::python::detail::referent_storage Chris@16: // Chris@16: #ifndef BOOST_PARAMETER_MAYBE_091021_HPP Chris@16: # define BOOST_PARAMETER_MAYBE_091021_HPP Chris@16: Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: # include Chris@16: Chris@16: namespace boost { namespace parameter { namespace aux { Chris@16: Chris@16: template struct referent_size; Chris@16: Chris@16: template Chris@16: struct referent_size Chris@16: { Chris@16: BOOST_STATIC_CONSTANT(std::size_t, value = sizeof(T)); Chris@16: }; Chris@16: Chris@16: // A metafunction returning a POD type which can store U, where T == Chris@16: // U&. If T is not a reference type, returns a POD which can store T. Chris@16: template Chris@16: struct referent_storage Chris@16: { Chris@16: typedef typename boost::aligned_storage< Chris@16: referent_size::value Chris@16: >::type type; Chris@16: }; Chris@16: Chris@16: template Chris@16: struct maybe : maybe_base Chris@16: { Chris@16: typedef typename add_reference< Chris@16: # if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564)) Chris@16: T const Chris@16: # else Chris@16: typename add_const::type Chris@16: # endif Chris@16: >::type reference; Chris@16: Chris@16: typedef typename remove_cv< Chris@16: BOOST_DEDUCED_TYPENAME remove_reference::type Chris@16: >::type non_cv_value; Chris@16: Chris@16: explicit maybe(T value_) Chris@16: : value(value_) Chris@16: , constructed(false) Chris@16: {} Chris@16: Chris@16: maybe() Chris@16: : constructed(false) Chris@16: {} Chris@16: Chris@16: ~maybe() Chris@16: { Chris@16: if (constructed) Chris@16: this->destroy(); Chris@16: } Chris@16: Chris@16: reference construct(reference value_) const Chris@16: { Chris@16: return value_; Chris@16: } Chris@16: Chris@16: template Chris@16: reference construct2(U const& value_) const Chris@16: { Chris@16: new (m_storage.address()) non_cv_value(value_); Chris@16: constructed = true; Chris@16: return *(non_cv_value*)m_storage.address(); Chris@16: } Chris@16: Chris@16: template Chris@16: reference construct(U const& value_) const Chris@16: { Chris@16: return this->construct2(value_); Chris@16: } Chris@16: Chris@16: void destroy() Chris@16: { Chris@16: ((non_cv_value*)m_storage.address())->~non_cv_value(); Chris@16: } Chris@16: Chris@16: typedef reference(maybe::*safe_bool)() const; Chris@16: Chris@16: operator safe_bool() const Chris@16: { Chris@16: return value ? &maybe::get : 0 ; Chris@16: } Chris@16: Chris@16: reference get() const Chris@16: { Chris@16: return value.get(); Chris@16: } Chris@16: Chris@16: private: Chris@16: boost::optional value; Chris@16: mutable bool constructed; Chris@16: Chris@16: Chris@16: mutable typename referent_storage< Chris@16: reference Chris@16: >::type m_storage; Chris@16: }; Chris@16: Chris@16: }}} // namespace boost::parameter::aux Chris@16: Chris@16: #endif // BOOST_PARAMETER_MAYBE_060211_HPP Chris@16: