Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r85613 - in branches/release: boost/utility boost/utility/detail libs/utility libs/utility/doc libs/utility/test
From: andrey.semashev_at_[hidden]
Date: 2013-09-08 15:28:44


Author: andysem
Date: 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013)
New Revision: 85613
URL: http://svn.boost.org/trac/boost/changeset/85613

Log:
Merged new added components from trunk. Merged other sublibraries which tests are passing for a long time as well.

Added:
   branches/release/boost/utility/empty_deleter.hpp (props changed)
      - copied unchanged from r85609, trunk/boost/utility/empty_deleter.hpp
   branches/release/boost/utility/explicit_operator_bool.hpp (props changed)
      - copied unchanged from r85609, trunk/boost/utility/explicit_operator_bool.hpp
   branches/release/libs/utility/doc/explicit_operator_bool.qbk (props changed)
      - copied unchanged from r85609, trunk/libs/utility/doc/explicit_operator_bool.qbk
   branches/release/libs/utility/test/explicit_operator_bool.cpp (props changed)
      - copied unchanged from r85609, trunk/libs/utility/test/explicit_operator_bool.cpp
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp (props changed)
      - copied unchanged from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp (props changed)
      - copied unchanged from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp (props changed)
      - copied unchanged from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp (props changed)
      - copied unchanged from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp
Text files modified:
   branches/release/boost/utility/base_from_member.hpp | 73 ++++++++++++++++++++++
   branches/release/boost/utility/declval.hpp | 41 +++++-------
   branches/release/boost/utility/detail/result_of_iterate.hpp | 23 +++++-
   branches/release/boost/utility/empty_deleter.hpp | 43 +++++++++++++
   branches/release/boost/utility/explicit_operator_bool.hpp | 128 ++++++++++++++++++++++++++++++++++++++++
   branches/release/boost/utility/result_of.hpp | 29 ++++++--
   branches/release/libs/utility/base_from_member.html | 53 ++++++++++++----
   branches/release/libs/utility/call_traits_test.cpp | 8 ++
   branches/release/libs/utility/doc/Jamfile.v2 | 21 +++++
   branches/release/libs/utility/doc/explicit_operator_bool.qbk | 68 +++++++++++++++++++++
   branches/release/libs/utility/index.html | 12 ++
   branches/release/libs/utility/test/Jamfile.v2 | 5 +
   branches/release/libs/utility/test/explicit_operator_bool.cpp | 54 ++++++++++++++++
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp | 40 ++++++++++++
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp | 40 ++++++++++++
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp | 40 ++++++++++++
   branches/release/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp | 40 ++++++++++++
   branches/release/libs/utility/test/result_of_test.cpp | 14 +++-
   branches/release/libs/utility/utility.htm | 40 ++++++++++++
   branches/release/libs/utility/value_init_test.cpp | 87 +++++++++++++--------------
   20 files changed, 754 insertions(+), 105 deletions(-)

Modified: branches/release/boost/utility/base_from_member.hpp
==============================================================================
--- branches/release/boost/utility/base_from_member.hpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/boost/utility/base_from_member.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -1,6 +1,6 @@
 // boost utility/base_from_member.hpp header file --------------------------//
 
-// Copyright 2001, 2003, 2004 Daryle Walker. Use, modification, and
+// Copyright 2001, 2003, 2004, 2012 Daryle Walker. Use, modification, and
 // distribution are subject to the Boost Software License, Version 1.0. (See
 // accompanying file LICENSE_1_0.txt or a copy at
 // <http://www.boost.org/LICENSE_1_0.txt>.)
@@ -10,10 +10,15 @@
 #ifndef BOOST_UTILITY_BASE_FROM_MEMBER_HPP
 #define BOOST_UTILITY_BASE_FROM_MEMBER_HPP
 
+#include <boost/config.hpp>
 #include <boost/preprocessor/arithmetic/inc.hpp>
 #include <boost/preprocessor/repetition/enum_binary_params.hpp>
 #include <boost/preprocessor/repetition/enum_params.hpp>
 #include <boost/preprocessor/repetition/repeat_from_to.hpp>
+#include <boost/type_traits/is_same.hpp>
+#include <boost/type_traits/remove_cv.hpp>
+#include <boost/type_traits/remove_reference.hpp>
+#include <boost/utility/enable_if.hpp>
 
 
 // Base-from-member arity configuration macro ------------------------------//
@@ -53,6 +58,59 @@
 namespace boost
 {
 
+namespace detail
+{
+
+// Type-unmarking class template -------------------------------------------//
+
+// Type-trait to get the raw type, i.e. the type without top-level reference nor
+// cv-qualification, from a type expression. Mainly for function arguments, any
+// reference part is stripped first.
+
+// Contributed by Daryle Walker
+
+template < typename T >
+struct remove_cv_ref
+{
+ typedef typename ::boost::remove_cv<typename
+ ::boost::remove_reference<T>::type>::type type;
+
+}; // boost::detail::remove_cv_ref
+
+// Unmarked-type comparison class template ---------------------------------//
+
+// Type-trait to check if two type expressions have the same raw type.
+
+// Contributed by Daryle Walker, based on a work-around by Luc Danton
+
+template < typename T, typename U >
+struct is_related
+ : public ::boost::is_same<
+ typename ::boost::detail::remove_cv_ref<T>::type,
+ typename ::boost::detail::remove_cv_ref<U>::type >
+{};
+
+// Enable-if-on-unidentical-unmarked-type class template -------------------//
+
+// Enable-if on the first two type expressions NOT having the same raw type.
+
+// Contributed by Daryle Walker, based on a work-around by Luc Danton
+
+#ifndef BOOST_NO_CXX11_VARIADIC_TEMPLATES
+template<typename ...T>
+struct enable_if_unrelated
+ : public ::boost::enable_if_c<true>
+{};
+
+template<typename T, typename U, typename ...U2>
+struct enable_if_unrelated<T, U, U2...>
+ : public ::boost::disable_if< ::boost::detail::is_related<T, U> >
+{};
+#endif
+
+} // namespace boost::detail
+
+
 // Base-from-member class template -----------------------------------------//
 
 // Helper to initialize a base object so a derived class can use this
@@ -68,12 +126,25 @@
 protected:
     MemberType member;
 
+#if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES) && \
+ !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && \
+ !defined(BOOST_NO_CXX11_FUNCTION_TEMPLATE_DEFAULT_ARGS) && \
+ !(defined(__GNUC__) && (__GNUC__ == 4) && (__GNUC_MINOR__ < 4))
+ template <typename ...T, typename EnableIf = typename
+ ::boost::detail::enable_if_unrelated<base_from_member, T...>::type>
+ explicit BOOST_CONSTEXPR base_from_member( T&& ...x )
+ BOOST_NOEXCEPT_IF( BOOST_NOEXCEPT_EXPR(::new ((void*) 0) MemberType(
+ static_cast<T&&>(x)... )) ) // no std::is_nothrow_constructible...
+ : member( static_cast<T&&>(x)... ) // ...nor std::forward needed
+ {}
+#else
     base_from_member()
         : member()
         {}
 
     BOOST_PP_REPEAT_FROM_TO( 1, BOOST_PP_INC(BOOST_BASE_FROM_MEMBER_MAX_ARITY),
      BOOST_PRIVATE_CTR_DEF, _ )
+#endif
 
 }; // boost::base_from_member
 

Modified: branches/release/boost/utility/declval.hpp
==============================================================================
--- branches/release/boost/utility/declval.hpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/boost/utility/declval.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -1,49 +1,44 @@
-// common_type.hpp ---------------------------------------------------------//
+// declval.hpp -------------------------------------------------------------//
 
 // Copyright 2010 Vicente J. Botet Escriba
 
 // Distributed under the Boost Software License, Version 1.0.
 // See http://www.boost.org/LICENSE_1_0.txt
 
-#ifndef BOOST_TYPE_TRAITS_EXT_DECLVAL__HPP
-#define BOOST_TYPE_TRAITS_EXT_DECLVAL__HPP
+#ifndef BOOST_UTILITY_DECLVAL_HPP
+#define BOOST_UTILITY_DECLVAL_HPP
 
 #include <boost/config.hpp>
 
 //----------------------------------------------------------------------------//
 
 #include <boost/type_traits/add_rvalue_reference.hpp>
-//#include <boost/type_traits/add_lvalue_reference.hpp>
 
 //----------------------------------------------------------------------------//
 // //
 // C++03 implementation of //
+// 20.2.4 Function template declval [declval] //
 // Written by Vicente J. Botet Escriba //
-//~ 20.3.4 Function template declval [declval]
-//~ 1 The library provides the function template declval to simplify the definition of expressions which occur as
-//~ unevaluated operands.
-//~ 2 Remarks: If this function is used, the program is ill-formed.
-//~ 3 Remarks: The template parameter T of declval may be an incomplete type.
-//~ [ Example:
-
-//~ template <class To, class From>
-//~ decltype(static_cast<To>(declval<From>())) convert(From&&);
-
-//~ declares a function template convert which only participats in overloading if the type From can be
-//~ explicitly converted to type To. For another example see class template common_type (20.7.6.6). —end
-//~ example ]
 // //
+// 1 The library provides the function template declval to simplify the
+// definition of expressions which occur as unevaluated operands.
+// 2 Remarks: If this function is used, the program is ill-formed.
+// 3 Remarks: The template parameter T of declval may be an incomplete type.
+// [ Example:
+//
+// template <class To, class From>
+// decltype(static_cast<To>(declval<From>())) convert(From&&);
+//
+// declares a function template convert which only participates in overloading
+// if the type From can be explicitly converted to type To. For another example
+// see class template common_type (20.9.7.6). -end example ]
 //----------------------------------------------------------------------------//
 
 namespace boost {
 
-//#if !defined(BOOST_NO_RVALUE_REFERENCES)
     template <typename T>
     typename add_rvalue_reference<T>::type declval() BOOST_NOEXCEPT; // as unevaluated operand
-//#else
-// template <typename T>
-// typename add_lvalue_reference<T>::type declval() BOOST_NOEXCEPT; // as unevaluated operand
-//#endif
+
 } // namespace boost
 
-#endif // BOOST_TYPE_TRAITS_EXT_DECLVAL__HPP
+#endif // BOOST_UTILITY_DECLVAL_HPP

Modified: branches/release/boost/utility/detail/result_of_iterate.hpp
==============================================================================
--- branches/release/boost/utility/detail/result_of_iterate.hpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/boost/utility/detail/result_of_iterate.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -38,10 +38,25 @@
 #endif
 
 #ifdef BOOST_RESULT_OF_USE_DECLTYPE
+template<typename F BOOST_PP_ENUM_TRAILING_PARAMS(BOOST_PP_ITERATION(),typename T)>
+struct result_of<F(BOOST_RESULT_OF_ARGS)>
+ : detail::cpp0x_result_of<F(BOOST_RESULT_OF_ARGS)> { };
+#endif // BOOST_RESULT_OF_USE_DECLTYPE
+
+#ifdef BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK
+template<typename F BOOST_PP_ENUM_TRAILING_PARAMS(BOOST_PP_ITERATION(),typename T)>
+struct result_of<F(BOOST_RESULT_OF_ARGS)>
+ : mpl::if_<mpl::or_<detail::has_result_type<F>, detail::has_result<F> >,
+ tr1_result_of<F(BOOST_RESULT_OF_ARGS)>,
+ detail::cpp0x_result_of<F(BOOST_RESULT_OF_ARGS)> >::type { };
+#endif // BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK
+
+#if defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)
+
+namespace detail {
 
-// Uses declval following N3225 20.7.7.6 when F is not a pointer.
 template<typename F BOOST_PP_ENUM_TRAILING_PARAMS(BOOST_PP_ITERATION(),typename T)>
-struct result_of<F(BOOST_PP_ENUM_PARAMS(BOOST_PP_ITERATION(),T))>
+struct cpp0x_result_of<F(BOOST_PP_ENUM_PARAMS(BOOST_PP_ITERATION(),T))>
     : mpl::if_<
           is_member_function_pointer<F>
         , detail::tr1_result_of_impl<
@@ -54,8 +69,6 @@
>::type
 {};
 
-namespace detail {
-
 #ifdef BOOST_NO_SFINAE_EXPR
 
 template<typename F>
@@ -139,7 +152,7 @@
 
 } // namespace detail
 
-#else // defined(BOOST_RESULT_OF_USE_DECLTYPE)
+#else // defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)
 
 #if !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551))
 template<typename F BOOST_PP_ENUM_TRAILING_PARAMS(BOOST_PP_ITERATION(),typename T)>

Copied: branches/release/boost/utility/empty_deleter.hpp (from r85609, trunk/boost/utility/empty_deleter.hpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/boost/utility/empty_deleter.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/boost/utility/empty_deleter.hpp)
@@ -0,0 +1,43 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file empty_deleter.hpp
+ * \author Andrey Semashev
+ * \date 22.04.2007
+ *
+ * This header contains an \c empty_deleter implementation. This is an empty
+ * function object that receives a pointer and does nothing with it.
+ * Such empty deletion strategy may be convenient, for example, when
+ * constructing <tt>shared_ptr</tt>s that point to some object that should not be
+ * deleted (i.e. a variable on the stack or some global singleton, like <tt>std::cout</tt>).
+ */
+
+#ifndef BOOST_UTILITY_EMPTY_DELETER_HPP_INCLUDED_
+#define BOOST_UTILITY_EMPTY_DELETER_HPP_INCLUDED_
+
+#include <boost/config.hpp>
+
+#ifdef BOOST_HAS_PRAGMA_ONCE
+#pragma once
+#endif
+
+namespace boost {
+
+//! A function object that does nothing and can be used as an empty deleter for \c shared_ptr
+struct empty_deleter
+{
+ //! Function object result type
+ typedef void result_type;
+ /*!
+ * Does nothing
+ */
+ void operator() (const volatile void*) const BOOST_NOEXCEPT {}
+};
+
+} // namespace boost
+
+#endif // BOOST_UTILITY_EMPTY_DELETER_HPP_INCLUDED_

Copied: branches/release/boost/utility/explicit_operator_bool.hpp (from r85609, trunk/boost/utility/explicit_operator_bool.hpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/boost/utility/explicit_operator_bool.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/boost/utility/explicit_operator_bool.hpp)
@@ -0,0 +1,128 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool.hpp
+ * \author Andrey Semashev
+ * \date 08.03.2009
+ *
+ * This header defines a compatibility macro that implements an unspecified
+ * \c bool operator idiom, which is superseded with explicit conversion operators in
+ * C++11.
+ */
+
+#ifndef BOOST_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_
+#define BOOST_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_
+
+#include <boost/config.hpp>
+
+#ifdef BOOST_HAS_PRAGMA_ONCE
+#pragma once
+#endif
+
+#if !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
+
+/*!
+ * \brief The macro defines an explicit operator of conversion to \c bool
+ *
+ * The macro should be used inside the definition of a class that has to
+ * support the conversion. The class should also implement <tt>operator!</tt>,
+ * in terms of which the conversion operator will be implemented.
+ */
+#define BOOST_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE explicit operator bool () const\
+ {\
+ return !this->operator! ();\
+ }
+
+/*!
+ * \brief The macro defines a constexpr explicit operator of conversion to \c bool
+ *
+ * The macro should be used inside the definition of a class that has to
+ * support the conversion. The class should also implement <tt>operator!</tt>,
+ * in terms of which the conversion operator will be implemented.
+ */
+#define BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE BOOST_CONSTEXPR explicit operator bool () const\
+ {\
+ return !this->operator! ();\
+ }
+
+#else // !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
+
+#if (defined(__SUNPRO_CC) && (__SUNPRO_CC <= 0x530)) && !defined(BOOST_NO_COMPILER_CONFIG)
+// Sun C++ 5.3 can't handle the safe_bool idiom, so don't use it
+#define BOOST_NO_UNSPECIFIED_BOOL
+#endif // (defined(__SUNPRO_CC) && (__SUNPRO_CC <= 0x530)) && !defined(BOOST_NO_COMPILER_CONFIG)
+
+#if !defined(BOOST_NO_UNSPECIFIED_BOOL)
+
+namespace boost {
+
+namespace detail {
+
+#if !defined(_MSC_VER) && !defined(__IBMCPP__)
+
+ struct unspecified_bool
+ {
+ // NOTE TO THE USER: If you see this in error messages then you tried
+ // to apply an unsupported operator on the object that supports
+ // explicit conversion to bool.
+ struct OPERATORS_NOT_ALLOWED;
+ static void true_value(OPERATORS_NOT_ALLOWED*) {}
+ };
+ typedef void (*unspecified_bool_type)(unspecified_bool::OPERATORS_NOT_ALLOWED*);
+
+#else
+
+ // MSVC and VACPP are too eager to convert pointer to function to void* even though they shouldn't
+ struct unspecified_bool
+ {
+ // NOTE TO THE USER: If you see this in error messages then you tried
+ // to apply an unsupported operator on the object that supports
+ // explicit conversion to bool.
+ struct OPERATORS_NOT_ALLOWED;
+ void true_value(OPERATORS_NOT_ALLOWED*) {}
+ };
+ typedef void (unspecified_bool::*unspecified_bool_type)(unspecified_bool::OPERATORS_NOT_ALLOWED*);
+
+#endif
+
+} // namespace detail
+
+} // namespace boost
+
+#define BOOST_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE operator boost::detail::unspecified_bool_type () const\
+ {\
+ return (!this->operator! () ? &boost::detail::unspecified_bool::true_value : (boost::detail::unspecified_bool_type)0);\
+ }
+
+#define BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE BOOST_CONSTEXPR operator boost::detail::unspecified_bool_type () const\
+ {\
+ return (!this->operator! () ? &boost::detail::unspecified_bool::true_value : (boost::detail::unspecified_bool_type)0);\
+ }
+
+#else // !defined(BOOST_NO_UNSPECIFIED_BOOL)
+
+#define BOOST_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE operator bool () const\
+ {\
+ return !this->operator! ();\
+ }
+
+#define BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()\
+ BOOST_FORCEINLINE BOOST_CONSTEXPR operator bool () const\
+ {\
+ return !this->operator! ();\
+ }
+
+#endif // !defined(BOOST_NO_UNSPECIFIED_BOOL)
+
+#endif // !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
+
+#endif // BOOST_UTILITY_EXPLICIT_OPERATOR_BOOL_HPP_INCLUDED_

Modified: branches/release/boost/utility/result_of.hpp
==============================================================================
--- branches/release/boost/utility/result_of.hpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/boost/utility/result_of.hpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -38,18 +38,27 @@
 
 // Use the decltype-based version of result_of by default if the compiler
 // supports N3276 <http://www.open-std.org/JTC1/SC22/WG21/docs/papers/2011/n3276.pdf>.
-// The user can force the choice by defining either BOOST_RESULT_OF_USE_DECLTYPE or
-// BOOST_RESULT_OF_USE_TR1, but not both!
-#if defined(BOOST_RESULT_OF_USE_DECLTYPE) && defined(BOOST_RESULT_OF_USE_TR1)
-# error Both BOOST_RESULT_OF_USE_DECLTYPE and BOOST_RESULT_OF_USE_TR1 cannot be defined at the same time.
+// The user can force the choice by defining BOOST_RESULT_OF_USE_DECLTYPE,
+// BOOST_RESULT_OF_USE_TR1, or BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK but not more than one!
+#if (defined(BOOST_RESULT_OF_USE_DECLTYPE) && defined(BOOST_RESULT_OF_USE_TR1)) || \
+ (defined(BOOST_RESULT_OF_USE_DECLTYPE) && defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)) || \
+ (defined(BOOST_RESULT_OF_USE_TR1) && defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK))
+# error More than one of BOOST_RESULT_OF_USE_DECLTYPE, BOOST_RESULT_OF_USE_TR1 and \
+ BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK cannot be defined at the same time.
+#endif
+
+#if defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK) && defined(BOOST_MPL_CFG_NO_HAS_XXX_TEMPLATE)
+# error Cannot fallback to decltype if BOOST_MPL_CFG_NO_HAS_XXX_TEMPLATE is not defined.
 #endif
 
 #ifndef BOOST_RESULT_OF_USE_TR1
 # ifndef BOOST_RESULT_OF_USE_DECLTYPE
-# ifndef BOOST_NO_CXX11_DECLTYPE_N3276 // this implies !defined(BOOST_NO_CXX11_DECLTYPE)
-# define BOOST_RESULT_OF_USE_DECLTYPE
-# else
-# define BOOST_RESULT_OF_USE_TR1
+# ifndef BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK
+# ifndef BOOST_NO_CXX11_DECLTYPE_N3276 // this implies !defined(BOOST_NO_CXX11_DECLTYPE)
+# define BOOST_RESULT_OF_USE_DECLTYPE
+# else
+# define BOOST_RESULT_OF_USE_TR1
+# endif
 # endif
 # endif
 #endif
@@ -64,8 +73,12 @@
 
 BOOST_MPL_HAS_XXX_TRAIT_DEF(result_type)
 
+BOOST_MPL_HAS_XXX_TEMPLATE_DEF(result)
+
 template<typename F, typename FArgs, bool HasResultType> struct tr1_result_of_impl;
 
+template<typename F> struct cpp0x_result_of;
+
 #ifdef BOOST_NO_SFINAE_EXPR
 
 // There doesn't seem to be any other way to turn this off such that the presence of

Modified: branches/release/libs/utility/base_from_member.html
==============================================================================
--- branches/release/libs/utility/base_from_member.html Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/base_from_member.html 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -129,6 +129,8 @@
 <h2><a name="synopsis">Synopsis</a></h2>
 
 <blockquote><pre>
+#include &lt;type_traits&gt; <i>// exposition only</i>
+
 #ifndef BOOST_BASE_FROM_MEMBER_MAX_ARITY
 #define BOOST_BASE_FROM_MEMBER_MAX_ARITY 10
 #endif
@@ -139,6 +141,11 @@
 protected:
     MemberType member;
 
+#if <i>C++2011 is in use</i>
+ template&lt; typename ...T &gt;
+ explicit constexpr base_from_member( T&amp;&amp; ...x )
+ noexcept( std::is_nothrow_constructible&lt;MemberType, T...&gt;::value );
+#else
     base_from_member();
 
     template&lt; typename T1 &gt;
@@ -154,6 +161,7 @@
      typename T10 &gt;
     base_from_member( T1 x1, T2 x2, T3 x3, T4 x4, T5 x5, T6 x6, T7 x7,
      T8 x8, T9 x9, T10 x10 );
+#endif
 };
 </pre></blockquote>
 
@@ -166,13 +174,29 @@
 data member called <var>member</var> that the derived class can use
 for later base classes (or itself).</p>
 
-<p>There is a default constructor and several constructor member
-templates. These constructor templates can take as many arguments
-(currently up to ten) as possible and pass them to a constructor of
-the data member. Since C++ does not allow any way to explicitly state
+<p>If the appropriate features of C++2011 are present, there will be a single
+constructor template. It implements &quot;perfect forwarding&quot; to the best
+constructor call of <code>member</code> (if any). The constructor template is
+marked both <code>constexpr</code> and <code>explicit</code>. The former will
+be ignored if the corresponding inner constructor call (of <code>member</code>)
+does not have the marker. The latter binds the other way; always taking
+effect, even when the inner constructor call does not have the marker. The
+constructor template propagates the <code>noexcept</code> status of the inner
+constructor call. (The constructor template has a trailing parameter with a
+default value that disables the template when its signature is too close to the
+signatures of the automatically-defined non-template copy- and/or
+move-constructors of <code>base_from_member</code>.)</p>
+
+<p>On earlier-standard compilers, there is a default constructor and several
+constructor member templates. These constructor templates can take as many
+arguments (currently up to ten) as possible and pass them to a constructor of
+the data member.</p>
+
+<p>Since C++ does not allow any way to explicitly state
 the template parameters of a templated constructor, make sure that
 the arguments are already close as possible to the actual type used in
-the data member's desired constructor.</p>
+the data member's desired constructor. Explicit conversions may be
+necessary.</p>
 
 <p>The <var>BOOST_BASE_FROM_MEMBER_MAX_ARITY</var> macro constant specifies
 the maximum argument length for the constructor templates. The constant
@@ -180,7 +204,7 @@
 constant may be read for code that is expandable like the class template and
 needs to maintain the same maximum size. (Example code would be a class that
 uses this class template as a base class for a member with a flexible set of
-constructors.)</p>
+constructors.) This constant is ignored when C++2011 features are present.</p>
 
 <h2><a name="usage">Usage</a></h2>
 
@@ -323,11 +347,14 @@
 argument for <code>pbase2_type</code> is converted from <code>int</code>
 to <code>double</code>. The second constructor argument for
 <code>pbase3_type</code> is a special case of necessary conversion; all
-forms of the null-pointer literal in C++ also look like compile-time
-integral expressions, so C++ always interprets such code as an integer
-when it has overloads that can take either an integer or a pointer. The
-last conversion is necessary for the compiler to call a constructor form
-with the exact pointer type used in <code>switcher</code>'s constructor.</p>
+forms of the null-pointer literal in C++ (except <code>nullptr</code> from
+C++2011) also look like compile-time integral expressions, so C++ always
+interprets such code as an integer when it has overloads that can take either
+an integer or a pointer. The last conversion is necessary for the compiler to
+call a constructor form with the exact pointer type used in
+<code>switcher</code>'s constructor. (If C++2011's <code>nullptr</code> is
+used, it still needs a conversion if multiple pointer types can be accepted in
+a constructor call but <code>std::nullptr_t</code> cannot.)</p>
 
 <h2><a name="credits">Credits</a></h2>
 
@@ -360,9 +387,9 @@
 
 <hr>
 
-<p>Revised: 28 August 2004</p>
+<p>Revised: 16 February 2012</p>
 
-<p>Copyright 2001, 2003, 2004 Daryle Walker. Use, modification, and distribution
+<p>Copyright 2001, 2003, 2004, 2012 Daryle Walker. Use, modification, and distribution
 are subject to the Boost Software License, Version 1.0. (See accompanying
 file LICENSE_1_0.txt or a copy at &lt;<a
 href="http://www.boost.org/LICENSE_1_0.txt">http://www.boost.org/LICENSE_1_0.txt>&gt;.)</p>

Modified: branches/release/libs/utility/call_traits_test.cpp
==============================================================================
--- branches/release/libs/utility/call_traits_test.cpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/call_traits_test.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -210,8 +210,10 @@
    comparible_UDT u;
    c1(u);
    call_traits_checker<int> c2;
+ call_traits_checker<enum_UDT> c2b;
    int i = 2;
    c2(i);
+ c2b(one);
    int* pi = &i;
    int a[2] = {1,2};
 #if defined(BOOST_MSVC6_MEMBER_TEMPLATES) && !defined(__ICL)
@@ -292,7 +294,11 @@
    BOOST_CHECK_TYPE(incomplete_type&, boost::call_traits<incomplete_type>::reference);
    BOOST_CHECK_TYPE(const incomplete_type&, boost::call_traits<incomplete_type>::const_reference);
    BOOST_CHECK_TYPE(const incomplete_type&, boost::call_traits<incomplete_type>::param_type);
-
+ // test enum:
+ BOOST_CHECK_TYPE(enum_UDT, boost::call_traits<enum_UDT>::value_type);
+ BOOST_CHECK_TYPE(enum_UDT&, boost::call_traits<enum_UDT>::reference);
+ BOOST_CHECK_TYPE(const enum_UDT&, boost::call_traits<enum_UDT>::const_reference);
+ BOOST_CHECK_TYPE(const enum_UDT, boost::call_traits<enum_UDT>::param_type);
    return 0;
 }
 

Modified: branches/release/libs/utility/doc/Jamfile.v2
==============================================================================
--- branches/release/libs/utility/doc/Jamfile.v2 Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/doc/Jamfile.v2 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -6,7 +6,7 @@
 project : requirements
         # Path for links to Boost:
         <xsl:param>boost.root=../../../..
-
+
         # Some general style settings:
         <xsl:param>table.footnote.number.format=1
         <xsl:param>footnote.number.format=1
@@ -59,7 +59,6 @@
         <xsl:param>toc.max.depth=1
         # How far down we go with TOC's
         <xsl:param>generate.section.toc.level=1
-
      ;
 
 xml string_ref : string_ref.qbk ;
@@ -79,5 +78,23 @@
         <xsl:param>toc.max.depth=1
         # How far down we go with TOC's
         <xsl:param>generate.section.toc.level=1
+ ;
 
+xml explicit_operator_bool : explicit_operator_bool.qbk ;
+boostbook standalone_explicit_operator_bool
+ :
+ explicit_operator_bool
+ :
+ # File name of HTML output:
+ <xsl:param>root.filename=explicit_operator_bool
+ # How far down we chunk nested sections, basically all of them:
+ <xsl:param>chunk.section.depth=0
+ # Don't put the first section on the same page as the TOC:
+ <xsl:param>chunk.first.sections=0
+ # How far down sections get TOC's
+ <xsl:param>toc.section.depth=1
+ # Max depth in each TOC:
+ <xsl:param>toc.max.depth=1
+ # How far down we go with TOC's
+ <xsl:param>generate.section.toc.level=1
      ;

Copied: branches/release/libs/utility/doc/explicit_operator_bool.qbk (from r85609, trunk/libs/utility/doc/explicit_operator_bool.qbk)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/doc/explicit_operator_bool.qbk 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/doc/explicit_operator_bool.qbk)
@@ -0,0 +1,68 @@
+[/
+ / Copyright (c) 2013 Andrey Semashev
+ /
+ / Distributed under the Boost Software License, Version 1.0. (See accompanying
+ / file LICENSE_1_0.txt or copy at
http://www.boost.org/LICENSE_1_0.txt)
+ /]
+
+[article BOOST_EXPLICIT_OPERATOR_BOOL and BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL
+ [quickbook 1.5]
+ [authors [Semashev, Andrey]]
+ [copyright 2013 Andrey Semashev]
+ [license
+ Distributed under the Boost Software License, Version 1.0.
+ (See accompanying file LICENSE_1_0.txt or copy at
+ [@http://www.boost.org/LICENSE_1_0.txt])
+ ]
+]
+
+[/===============]
+[section Overview]
+[/===============]
+
+`BOOST_EXPLICIT_OPERATOR_BOOL()` and `BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()` are compatibility helper macros that expand to an explicit conversion operator to `bool`. For compilers not supporting explicit conversion operators introduced in C++11 the macros expand to a conversion operator that implements the [@http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Safe_bool safe bool idiom]. In case if the compiler is not able to handle safe bool idiom well the macros expand to a regular conversion operator to `bool`.
+
+[endsect]
+
+
+[/===============]
+[section Examples]
+[/===============]
+
+Both macros are intended to be placed within a user's class definition. The generated conversion operators will be implemented in terms of `operator!()` that should be defined by user in this class. In case of `BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()` the generated conversion operator will be declared `constexpr` which requires the corresponding `operator!()` to also be `constexpr`.
+
+ template< typename T >
+ class my_ptr
+ {
+ T* m_p;
+
+ public:
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+
+ bool operator!() const
+ {
+ return !m_p;
+ }
+ };
+
+Now `my_ptr` can be used in conditional expressions, similarly to a regular pointer:
+
+ my_ptr< int > p;
+ if (p)
+ std::cout << "true" << std::endl;
+
+[endsect]
+
+[/===============]
+[section History]
+[/===============]
+
+[heading boost 1.55]
+
+* The macro was extracted from Boost.Log.
+
+[endsect]
+
+
+
+

Modified: branches/release/libs/utility/index.html
==============================================================================
--- branches/release/libs/utility/index.html Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/index.html 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -14,22 +14,29 @@
                 <p>But that doesn't mean there isn't useful stuff here. Take a look:</p>
                 <blockquote>
                         <p>
+ addressof<br>
                                 <a href="assert.html">assert</a><br>
                                 <a href="base_from_member.html">base_from_member</a><br>
+ BOOST_BINARY<br>
                                 <a href="call_traits.htm">call_traits</a><br>
                                 <a href="checked_delete.html">checked_delete</a><br>
                                 <a href="compressed_pair.htm">compressed_pair</a><br>
                                 <a href="current_function.html">current_function</a><br>
                                 <a href="doc/html/declval.html">declval</a><br>
                                 <a href="enable_if.html">enable_if</a><br>
- iterator_adaptors<br>
- generator iterator adaptors<br>
+ in_place_factory<br>
+ iterator_adaptors<br>
+ generator iterator adaptors<br>
+ next/prior<br>
+ noncopyable<br>
                                 <a href="operators.htm">operators</a><br>
+ result_of<br>
                                 <a href="swap.html">swap</a><br>
                                 <a href="throw_exception.html">throw_exception</a><br>
                                 <a href="utility.htm">utility</a><br>
             <a href="doc/html/string_ref.html">string_ref</a><br>
             <a href="value_init.htm">value_init</a>
+ BOOST_EXPLICIT_OPERATOR_BOOL and BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL<br>
          </p>
                 </blockquote>
                 <hr>
@@ -43,4 +50,3 @@
                         <!--webbot bot="Timestamp" S-Type="EDITED" S-Format="%d %B, %Y" startspan -->07 November, 2006<!--webbot bot="Timestamp" endspan i-checksum="39368" --></p>
                 </body>
 </html>
-

Modified: branches/release/libs/utility/test/Jamfile.v2
==============================================================================
--- branches/release/libs/utility/test/Jamfile.v2 Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/test/Jamfile.v2 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -48,5 +48,10 @@
         [ compile-fail ../initialized_test_fail1.cpp ]
         [ compile-fail ../initialized_test_fail2.cpp ]
         [ run ../verify_test.cpp ]
+ [ run explicit_operator_bool.cpp ]
+ [ compile-fail explicit_operator_bool_compile_fail_conv_int.cpp ]
+ [ compile-fail explicit_operator_bool_compile_fail_conv_pvoid.cpp ]
+ [ compile-fail explicit_operator_bool_compile_fail_delete.cpp ]
+ [ compile-fail explicit_operator_bool_compile_fail_shift.cpp ]
     ;
 

Copied: branches/release/libs/utility/test/explicit_operator_bool.cpp (from r85609, trunk/libs/utility/test/explicit_operator_bool.cpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/test/explicit_operator_bool.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/test/explicit_operator_bool.cpp)
@@ -0,0 +1,54 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool_compile.cpp
+ * \author Andrey Semashev
+ * \date 17.07.2010
+ *
+ * \brief This test checks that explicit operator bool can be used in
+ * the valid contexts.
+ */
+
+#define BOOST_TEST_MODULE explicit_operator_bool_compile
+
+#include <boost/utility/explicit_operator_bool.hpp>
+
+namespace {
+
+ // A test object that has the operator of explicit conversion to bool
+ struct checkable1
+ {
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+ bool operator! () const
+ {
+ return false;
+ }
+ };
+
+ struct checkable2
+ {
+ BOOST_CONSTEXPR_EXPLICIT_OPERATOR_BOOL()
+ BOOST_CONSTEXPR bool operator! () const
+ {
+ return false;
+ }
+ };
+
+} // namespace
+
+int main(int, char*[])
+{
+ checkable1 val1;
+ if (val1)
+ {
+ checkable2 val2;
+ if (val2)
+ return 0;
+ }
+
+ return 1;
+}

Copied: branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp (from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_int.cpp)
@@ -0,0 +1,40 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool_compile_fail_conv_int.cpp
+ * \author Andrey Semashev
+ * \date 17.07.2010
+ *
+ * \brief This test checks that explicit operator bool cannot be used in
+ * an unintended context.
+ */
+
+#define BOOST_TEST_MODULE explicit_operator_bool_compile_fail_conv_int
+
+#include <boost/utility/explicit_operator_bool.hpp>
+
+namespace {
+
+ // A test object that has the operator of explicit conversion to bool
+ struct checkable
+ {
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+ bool operator! () const
+ {
+ return false;
+ }
+ };
+
+} // namespace
+
+int main(int, char*[])
+{
+ checkable val;
+ int n = val;
+
+ return 0;
+}

Copied: branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp (from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_conv_pvoid.cpp)
@@ -0,0 +1,40 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool_compile_fail_conv_pvoid.cpp
+ * \author Andrey Semashev
+ * \date 17.07.2010
+ *
+ * \brief This test checks that explicit operator bool cannot be used in
+ * an unintended context.
+ */
+
+#define BOOST_TEST_MODULE explicit_operator_bool_compile_fail_conv_pvoid
+
+#include <boost/utility/explicit_operator_bool.hpp>
+
+namespace {
+
+ // A test object that has the operator of explicit conversion to bool
+ struct checkable
+ {
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+ bool operator! () const
+ {
+ return false;
+ }
+ };
+
+} // namespace
+
+int main(int, char*[])
+{
+ checkable val;
+ void* p = val;
+
+ return 0;
+}

Copied: branches/release/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp (from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_delete.cpp)
@@ -0,0 +1,40 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool_compile_fail_delete.cpp
+ * \author Andrey Semashev
+ * \date 17.07.2010
+ *
+ * \brief This test checks that explicit operator bool cannot be used in
+ * an unintended context.
+ */
+
+#define BOOST_TEST_MODULE util_explicit_operator_bool_delete
+
+#include <boost/utility/explicit_operator_bool.hpp>
+
+namespace {
+
+ // A test object that has the operator of explicit conversion to bool
+ struct checkable
+ {
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+ bool operator! () const
+ {
+ return false;
+ }
+ };
+
+} // namespace
+
+int main(int, char*[])
+{
+ checkable val;
+ delete val;
+
+ return 0;
+}

Copied: branches/release/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp (from r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp)
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ branches/release/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613, copy of r85609, trunk/libs/utility/test/explicit_operator_bool_compile_fail_shift.cpp)
@@ -0,0 +1,40 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2013.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file explicit_operator_bool_compile_fail_shift.cpp
+ * \author Andrey Semashev
+ * \date 17.07.2010
+ *
+ * \brief This test checks that explicit operator bool cannot be used in
+ * an unintended context.
+ */
+
+#define BOOST_TEST_MODULE explicit_operator_bool_compile_fail_shift
+
+#include <boost/utility/explicit_operator_bool.hpp>
+
+namespace {
+
+ // A test object that has the operator of explicit conversion to bool
+ struct checkable
+ {
+ BOOST_EXPLICIT_OPERATOR_BOOL()
+ bool operator! () const
+ {
+ return false;
+ }
+ };
+
+} // namespace
+
+int main(int, char*[])
+{
+ checkable val;
+ val << 2;
+
+ return 0;
+}

Modified: branches/release/libs/utility/test/result_of_test.cpp
==============================================================================
--- branches/release/libs/utility/test/result_of_test.cpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/test/result_of_test.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -5,6 +5,12 @@
 // 1.0. (See accompanying file LICENSE_1_0.txt or copy at
 // http://www.boost.org/LICENSE_1_0.txt)
 
+// Examples:
+// To run the default test:
+// $ cd libs/utility/test && bjam
+// To test decltype on g++ 2.7:
+// $ cd libs/utility/test && bjam cxxflags="-std=c++11 -D BOOST_RESULT_OF_USE_DECLTYPE"
+
 #include <boost/config.hpp>
 
 // For more information, see http://www.boost.org/libs/utility
@@ -190,7 +196,7 @@
   BOOST_STATIC_ASSERT((is_same<tr1_result_of<volatile int_result_of_template<void>(void)>::type, void>::value));
 
   // Prior to decltype, result_of could not deduce the return type
- // nullary function objects unless they exposed a result_type.
+ // of nullary function objects unless they exposed a result_type.
 #if defined(BOOST_RESULT_OF_USE_DECLTYPE)
   BOOST_STATIC_ASSERT((is_same<result_of<int_result_of(void)>::type, int>::value));
   BOOST_STATIC_ASSERT((is_same<result_of<volatile int_result_of(void)>::type, int>::value));
@@ -273,7 +279,7 @@
   BOOST_STATIC_ASSERT((is_same<tr1_result_of<pf_t(int)>::type, int>::value));
   BOOST_STATIC_ASSERT((is_same<tr1_result_of<pf_t const(int)>::type,int>::value));
 
-#if defined(BOOST_RESULT_OF_USE_DECLTYPE)
+#if defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)
   BOOST_STATIC_ASSERT((is_same<result_of<no_result_type_or_result(double)>::type, short>::value));
   BOOST_STATIC_ASSERT((is_same<result_of<const no_result_type_or_result(double)>::type, cv_overload_check<const short> >::value));
   BOOST_STATIC_ASSERT((is_same<result_of<volatile no_result_type_or_result(double)>::type, cv_overload_check<volatile short> >::value));
@@ -301,10 +307,10 @@
 #endif
 #endif
 
-#if defined(BOOST_RESULT_OF_USE_DECLTYPE)
+#if defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)
   int i = 123;
   sfinae_test(sfinae_test_f, i);
-#endif // defined(BOOST_RESULT_OF_USE_DECLTYPE)
+#endif // defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK)
 
   return 0;
 }

Modified: branches/release/libs/utility/utility.htm
==============================================================================
--- branches/release/libs/utility/utility.htm Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/utility.htm 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -259,6 +259,46 @@
                 represent the return type of
                 <code>operator()</code> given a call expression.</p>
 
+ <p>Additionally, <code>boost::result_of</code>
+ provides a third mode of operation, which some users
+ may find convenient. When
+ <code>BOOST_RESULT_OF_USE_TR1_WITH_DECLTYPE_FALLBACK</code>
+ is defined, <code>boost::result_of</code> behaves as
+ follows. If the function object has a member
+ type <code>result_type</code> or member
+ template <code>result&lt;&gt;</code>, then
+ <code>boost::result_of</code> will use the TR1
+ protocol. Otherwise,
+ <code>boost::result_of</code> will
+ use <code>decltype</code>. Using TR1 with
+ a <code>declytpe</code> fallback may workaround
+ certain problems at the cost of portability. For
+ example:
+ <ul>
+ <li>Deficient compiler: If your code
+ requires <code>boost::result_of</code> to work
+ with incomplete return types but your
+ compiler's <code>decltype</code> implementation
+ does not support incomplete return types, then you
+ can use the TR1 protocol as a workaround. Support
+ for incomplete return types was added late in the
+ C++11 standardization process
+ (see N3276)
+ and is not implemented by some compilers.</li>
+
+ <li>Deficient legacy code: If your existing TR1
+ function object advertises a different type than
+ the actual result type deduced
+ by <code>decltype</code>, then using TR1 with a
+ <code>decltype</code> fallback will allow you to
+ work with both your existing TR1 function objects
+ and new C++11 function object. This situation
+ could occur if your legacy function objects
+ misused the TR1 protocol. See the documentation on
+ known differences
+ between <code>boost::result_of</code> and TR1.</li>
+ </ul>
+
                 <a name="BOOST_NO_RESULT_OF"></a>
                 <p>This implementation of <code>result_of</code>
                 requires class template partial specialization, the

Modified: branches/release/libs/utility/value_init_test.cpp
==============================================================================
--- branches/release/libs/utility/value_init_test.cpp Sun Sep 8 14:58:21 2013 (r85612)
+++ branches/release/libs/utility/value_init_test.cpp 2013-09-08 15:28:44 EDT (Sun, 08 Sep 2013) (r85613)
@@ -22,7 +22,7 @@
 #pragma hdrstop
 #endif
 
-#include "boost/test/minimal.hpp"
+#include <boost/detail/lightweight_test.hpp>
 
 //
 // Sample POD type
@@ -215,7 +215,7 @@
 void check_initialized_value ( T const& y )
 {
   T initializedValue = boost::initialized_value ;
- BOOST_CHECK ( y == initializedValue ) ;
+ BOOST_TEST ( y == initializedValue ) ;
 }
 
 #ifdef __BORLANDC__
@@ -245,128 +245,125 @@
 template<class T>
 bool test ( T const& y, T const& z )
 {
- const boost::unit_test::counter_t counter_before_test = boost::minimal_test::errors_counter();
+ const int errors_before_test = boost::detail::test_errors();
 
   check_initialized_value(y);
 
   boost::value_initialized<T> x ;
- BOOST_CHECK ( y == x ) ;
- BOOST_CHECK ( y == boost::get(x) ) ;
+ BOOST_TEST ( y == x ) ;
+ BOOST_TEST ( y == boost::get(x) ) ;
 
   static_cast<T&>(x) = z ;
   boost::get(x) = z ;
- BOOST_CHECK ( x == z ) ;
+ BOOST_TEST ( x == z ) ;
 
   boost::value_initialized<T> const x_c ;
- BOOST_CHECK ( y == x_c ) ;
- BOOST_CHECK ( y == boost::get(x_c) ) ;
+ BOOST_TEST ( y == x_c ) ;
+ BOOST_TEST ( y == boost::get(x_c) ) ;
   T& x_c_ref = const_cast<T&>( boost::get(x_c) ) ;
   x_c_ref = z ;
- BOOST_CHECK ( x_c == z ) ;
+ BOOST_TEST ( x_c == z ) ;
 
   boost::value_initialized<T> const copy1 = x;
- BOOST_CHECK ( boost::get(copy1) == boost::get(x) ) ;
+ BOOST_TEST ( boost::get(copy1) == boost::get(x) ) ;
 
   boost::value_initialized<T> copy2;
   copy2 = x;
- BOOST_CHECK ( boost::get(copy2) == boost::get(x) ) ;
+ BOOST_TEST ( boost::get(copy2) == boost::get(x) ) ;
   
   boost::shared_ptr<boost::value_initialized<T> > ptr( new boost::value_initialized<T> );
- BOOST_CHECK ( y == *ptr ) ;
+ BOOST_TEST ( y == *ptr ) ;
 
 #if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
   boost::value_initialized<T const> cx ;
- BOOST_CHECK ( y == cx ) ;
- BOOST_CHECK ( y == boost::get(cx) ) ;
+ BOOST_TEST ( y == cx ) ;
+ BOOST_TEST ( y == boost::get(cx) ) ;
 
   boost::value_initialized<T const> const cx_c ;
- BOOST_CHECK ( y == cx_c ) ;
- BOOST_CHECK ( y == boost::get(cx_c) ) ;
+ BOOST_TEST ( y == cx_c ) ;
+ BOOST_TEST ( y == boost::get(cx_c) ) ;
 #endif
 
- return boost::minimal_test::errors_counter() == counter_before_test ;
+ return boost::detail::test_errors() == errors_before_test ;
 }
 
-int test_main(int, char **)
+int main(int, char **)
 {
- BOOST_CHECK ( test( 0,1234 ) ) ;
- BOOST_CHECK ( test( 0.0,12.34 ) ) ;
- BOOST_CHECK ( test( POD(0,0,0.0), POD('a',1234,56.78f) ) ) ;
- BOOST_CHECK ( test( NonPOD( std::string() ), NonPOD( std::string("something") ) ) ) ;
+ BOOST_TEST ( test( 0,1234 ) ) ;
+ BOOST_TEST ( test( 0.0,12.34 ) ) ;
+ BOOST_TEST ( test( POD(0,0,0.0), POD('a',1234,56.78f) ) ) ;
+ BOOST_TEST ( test( NonPOD( std::string() ), NonPOD( std::string("something") ) ) ) ;
 
   NonPOD NonPOD_object( std::string("NonPOD_object") );
- BOOST_CHECK ( test<NonPOD *>( 0, &NonPOD_object ) ) ;
+ BOOST_TEST ( test<NonPOD *>( 0, &NonPOD_object ) ) ;
 
   AggregatePODStruct zeroInitializedAggregatePODStruct = { 0.0f, '\0', 0 };
   AggregatePODStruct nonZeroInitializedAggregatePODStruct = { 1.25f, 'a', -1 };
- BOOST_CHECK ( test(zeroInitializedAggregatePODStruct, nonZeroInitializedAggregatePODStruct) );
+ BOOST_TEST ( test(zeroInitializedAggregatePODStruct, nonZeroInitializedAggregatePODStruct) );
 
   StringAndInt stringAndInt0;
   StringAndInt stringAndInt1;
   stringAndInt0.i = 0;
   stringAndInt1.i = 1;
   stringAndInt1.s = std::string("1");
- BOOST_CHECK ( test(stringAndInt0, stringAndInt1) );
+ BOOST_TEST ( test(stringAndInt0, stringAndInt1) );
 
   StructWithDestructor structWithDestructor0;
   StructWithDestructor structWithDestructor1;
   structWithDestructor0.i = 0;
   structWithDestructor1.i = 1;
- BOOST_CHECK ( test(structWithDestructor0, structWithDestructor1) );
+ BOOST_TEST ( test(structWithDestructor0, structWithDestructor1) );
 
   StructWithVirtualFunction structWithVirtualFunction0;
   StructWithVirtualFunction structWithVirtualFunction1;
   structWithVirtualFunction0.i = 0;
   structWithVirtualFunction1.i = 1;
- BOOST_CHECK ( test(structWithVirtualFunction0, structWithVirtualFunction1) );
+ BOOST_TEST ( test(structWithVirtualFunction0, structWithVirtualFunction1) );
 
   DerivedFromAggregatePODStruct derivedFromAggregatePODStruct0;
   DerivedFromAggregatePODStruct derivedFromAggregatePODStruct1;
   static_cast<AggregatePODStruct &>(derivedFromAggregatePODStruct0) = zeroInitializedAggregatePODStruct;
   static_cast<AggregatePODStruct &>(derivedFromAggregatePODStruct1) = nonZeroInitializedAggregatePODStruct;
- BOOST_CHECK ( test(derivedFromAggregatePODStruct0, derivedFromAggregatePODStruct1) );
+ BOOST_TEST ( test(derivedFromAggregatePODStruct0, derivedFromAggregatePODStruct1) );
 
   AggregatePODStructWrapper aggregatePODStructWrapper0;
   AggregatePODStructWrapper aggregatePODStructWrapper1;
   aggregatePODStructWrapper0.dataMember = zeroInitializedAggregatePODStruct;
   aggregatePODStructWrapper1.dataMember = nonZeroInitializedAggregatePODStruct;
- BOOST_CHECK ( test(aggregatePODStructWrapper0, aggregatePODStructWrapper1) );
+ BOOST_TEST ( test(aggregatePODStructWrapper0, aggregatePODStructWrapper1) );
 
   ArrayOfBytes zeroInitializedArrayOfBytes = { 0 };
   boost::value_initialized<ArrayOfBytes> valueInitializedArrayOfBytes;
- BOOST_CHECK (std::memcmp(get(valueInitializedArrayOfBytes), zeroInitializedArrayOfBytes, sizeof(ArrayOfBytes)) == 0);
+ BOOST_TEST (std::memcmp(get(valueInitializedArrayOfBytes), zeroInitializedArrayOfBytes, sizeof(ArrayOfBytes)) == 0);
 
   boost::value_initialized<ArrayOfBytes> valueInitializedArrayOfBytes2;
   valueInitializedArrayOfBytes2 = valueInitializedArrayOfBytes;
- BOOST_CHECK (std::memcmp(get(valueInitializedArrayOfBytes), get(valueInitializedArrayOfBytes2), sizeof(ArrayOfBytes)) == 0);
+ BOOST_TEST (std::memcmp(get(valueInitializedArrayOfBytes), get(valueInitializedArrayOfBytes2), sizeof(ArrayOfBytes)) == 0);
 
   boost::value_initialized<CopyFunctionCallTester> copyFunctionCallTester1;
- BOOST_CHECK ( ! get(copyFunctionCallTester1).is_copy_constructed);
- BOOST_CHECK ( ! get(copyFunctionCallTester1).is_assignment_called);
+ BOOST_TEST ( ! get(copyFunctionCallTester1).is_copy_constructed);
+ BOOST_TEST ( ! get(copyFunctionCallTester1).is_assignment_called);
 
   boost::value_initialized<CopyFunctionCallTester> copyFunctionCallTester2 = boost::value_initialized<CopyFunctionCallTester>(copyFunctionCallTester1);
- BOOST_CHECK ( get(copyFunctionCallTester2).is_copy_constructed);
- BOOST_CHECK ( ! get(copyFunctionCallTester2).is_assignment_called);
+ BOOST_TEST ( get(copyFunctionCallTester2).is_copy_constructed);
+ BOOST_TEST ( ! get(copyFunctionCallTester2).is_assignment_called);
 
   boost::value_initialized<CopyFunctionCallTester> copyFunctionCallTester3;
   copyFunctionCallTester3 = boost::value_initialized<CopyFunctionCallTester>(copyFunctionCallTester1);
- BOOST_CHECK ( ! get(copyFunctionCallTester3).is_copy_constructed);
- BOOST_CHECK ( get(copyFunctionCallTester3).is_assignment_called);
+ BOOST_TEST ( ! get(copyFunctionCallTester3).is_copy_constructed);
+ BOOST_TEST ( get(copyFunctionCallTester3).is_assignment_called);
 
   boost::value_initialized<SwapFunctionCallTester> swapFunctionCallTester1;
   boost::value_initialized<SwapFunctionCallTester> swapFunctionCallTester2;
   get(swapFunctionCallTester1).data = 1;
   get(swapFunctionCallTester2).data = 2;
   boost::swap(swapFunctionCallTester1, swapFunctionCallTester2);
- BOOST_CHECK( get(swapFunctionCallTester1).data == 2 );
- BOOST_CHECK( get(swapFunctionCallTester2).data == 1 );
- BOOST_CHECK( get(swapFunctionCallTester1).is_custom_swap_called );
- BOOST_CHECK( get(swapFunctionCallTester2).is_custom_swap_called );
+ BOOST_TEST( get(swapFunctionCallTester1).data == 2 );
+ BOOST_TEST( get(swapFunctionCallTester2).data == 1 );
+ BOOST_TEST( get(swapFunctionCallTester1).is_custom_swap_called );
+ BOOST_TEST( get(swapFunctionCallTester2).is_custom_swap_called );
 
- return 0;
+ return boost::report_errors();
 }
 
 
-unsigned int expected_failures = 0;
-
-


Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk