aboutsummaryrefslogtreecommitdiff
path: root/libstdc++-v3
diff options
context:
space:
mode:
authorPaolo Carlini <paolo@gcc.gnu.org>2011-04-30 19:40:06 +0000
committerPaolo Carlini <paolo@gcc.gnu.org>2011-04-30 19:40:06 +0000
commit2c7a09d774a2af28c51224404ba47f5f7c182cea (patch)
tree216363d5372c9b247b77a0955e69523ffad3fc97 /libstdc++-v3
parent2ad7ae18f41c0fc42e0d68978bb0fdb4f6f7c3a5 (diff)
downloadgcc-2c7a09d774a2af28c51224404ba47f5f7c182cea.zip
gcc-2c7a09d774a2af28c51224404ba47f5f7c182cea.tar.gz
gcc-2c7a09d774a2af28c51224404ba47f5f7c182cea.tar.bz2
[multiple changes]
2011-04-30 Daniel Krugler <daniel.kruegler@googlemail.com> * include/std/type_traits (__is_default_constructible_atom, __is_default_constructible_safe<, true>, __is_direct_constructible_new_safe, __is_base_to_derived_ref<,, true>, __is_lvalue_to_rvalue_ref<,, true>, __is_direct_constructible_ref_cast, __is_direct_constructible, __is_nary_constructible): Simplify; add comments throughout. 2011-04-30 Paolo Carlini <paolo.carlini@oracle.com> * testsuite/20_util/make_signed/requirements/typedefs_neg.cc: Adjust dg-error line numbers. * testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc: Likewise. * testsuite/20_util/declval/requirements/1_neg.cc: Likewise. From-SVN: r173222
Diffstat (limited to 'libstdc++-v3')
-rw-r--r--libstdc++-v3/ChangeLog17
-rw-r--r--libstdc++-v3/include/std/type_traits84
-rw-r--r--libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc2
-rw-r--r--libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc4
-rw-r--r--libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc4
5 files changed, 70 insertions, 41 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog
index 5dfeb77..8e509aa 100644
--- a/libstdc++-v3/ChangeLog
+++ b/libstdc++-v3/ChangeLog
@@ -1,3 +1,20 @@
+2011-04-30 Daniel Krugler <daniel.kruegler@googlemail.com>
+
+ * include/std/type_traits (__is_default_constructible_atom,
+ __is_default_constructible_safe<, true>,
+ __is_direct_constructible_new_safe,
+ __is_base_to_derived_ref<,, true>, __is_lvalue_to_rvalue_ref<,, true>,
+ __is_direct_constructible_ref_cast, __is_direct_constructible,
+ __is_nary_constructible): Simplify; add comments throughout.
+
+2011-04-30 Paolo Carlini <paolo.carlini@oracle.com>
+
+ * testsuite/20_util/make_signed/requirements/typedefs_neg.cc:
+ Adjust dg-error line numbers.
+ * testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc:
+ Likewise.
+ * testsuite/20_util/declval/requirements/1_neg.cc: Likewise.
+
2011-04-30 Doug Kwan <dougkwan@google.com>
* include/Makefile.am (install-freestanding-headers): Also install
diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits
index 6d33416..0560522 100644
--- a/libstdc++-v3/include/std/type_traits
+++ b/libstdc++-v3/include/std/type_traits
@@ -550,7 +550,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
struct __is_array_unknown_bounds
: public __and_<is_array<_Tp>, __not_<extent<_Tp>>>::type
{ };
-
+
+ // In N3290 is_destructible does not say anything about function
+ // types and abstract types, see LWG 2049. This implementation
+ // describes function types as trivially nothrow destructible and
+ // abstract types as destructible, iff the explicit destructor
+ // call expression is wellformed.
struct __do_is_destructible_impl_1
{
template<typename _Up>
@@ -571,6 +576,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typedef decltype(__test<_Tp>(0)) type;
};
+ // Special implementation for abstract types
struct __do_is_destructible_impl_2
{
template<typename _Tp, typename = decltype(declval<_Tp&>().~_Tp())>
@@ -632,23 +638,23 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Tp>
struct __is_default_constructible_atom
- : public __and_<is_destructible<_Tp>,
- __is_default_constructible_impl<_Tp>>::type::type
+ : public __and_<__not_<is_void<_Tp>>,
+ __is_default_constructible_impl<_Tp>>::type
{ };
template<typename _Tp, bool = is_array<_Tp>::value>
struct __is_default_constructible_safe;
- // The following technique is a workaround for a gcc defect, which does
- // not sfinae away attempts to default-construct arrays of unknown bounds.
- // Complete arrays can be default-constructed, if the element type is
- // default-constructible, but arrays with unknown bounds are not:
-
+ // The following technique is a workaround for a current core language
+ // restriction, which does not allow for array types to occur in
+ // functional casts of the form T(). Complete arrays can be default-
+ // constructed, if the element type is default-constructible, but
+ // arrays with unknown bounds are not.
template<typename _Tp>
struct __is_default_constructible_safe<_Tp, true>
: public __and_<__is_array_known_bounds<_Tp>,
__is_default_constructible_atom<typename
- remove_all_extents<_Tp>::type>>::type::type
+ remove_all_extents<_Tp>::type>>::type
{ };
template<typename _Tp>
@@ -663,6 +669,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_Tp>::value)>
{ };
+
+ // Implementation of is_constructible.
+
+ // The hardest part of this trait is the binary direct-initialization
+ // case, because we hit into a functional cast of the form T(arg).
+ // This implementation uses different strategies depending on the
+ // target type to reduce the test overhead as much as possible:
+ //
+ // a) For a reference target type, we use a static_cast expression
+ // modulo its extra cases.
+ //
+ // b) For a non-reference target type we use a ::new expression.
struct __do_is_static_castable_impl
{
template<typename _From, typename _To, typename
@@ -682,8 +700,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _From, typename _To>
struct __is_static_castable_safe
- : public __and_<__or_<is_void<_To>, is_destructible<_To>>,
- __is_static_castable_impl<_From, _To>>::type::type
+ : public __is_static_castable_impl<_From, _To>::type
{ };
// __is_static_castable
@@ -693,6 +710,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_From, _To>::value)>
{ };
+ // Implementation for non-reference types. To meet the proper
+ // variable definition semantics, we also need to test for
+ // is_destructible in this case.
struct __do_is_direct_constructible_impl
{
template<typename _Tp, typename _Arg, typename
@@ -713,7 +733,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Tp, typename _Arg>
struct __is_direct_constructible_new_safe
: public __and_<is_destructible<_Tp>,
- __is_direct_constructible_impl<_Tp, _Arg>>::type::type
+ __is_direct_constructible_impl<_Tp, _Arg>>::type
{ };
template<typename, typename>
@@ -736,10 +756,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>::type>::type __src_t;
typedef typename remove_cv<typename remove_reference<_To
>::type>::type __dst_t;
- typedef typename __and_<
- __not_<is_same<__src_t, __dst_t>>,
- is_base_of<__src_t, __dst_t>
- >::type type;
+ typedef __and_<__not_<is_same<__src_t, __dst_t>>,
+ is_base_of<__src_t, __dst_t>> type;
static constexpr bool value = type::value;
};
@@ -760,10 +778,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
_From>::type>::type __src_t;
typedef typename remove_cv<typename remove_reference<
_To>::type>::type __dst_t;
- typedef typename __or_<
- is_same<__src_t, __dst_t>,
- is_base_of<__dst_t, __src_t>
- >::type type;
+ typedef __or_<is_same<__src_t, __dst_t>,
+ is_base_of<__dst_t, __src_t>> type;
static constexpr bool value = type::value;
};
@@ -772,25 +788,20 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
: public false_type
{ };
- // Here we handle direct-initialization to a reference type
- // as equivalent to a static_cast modulo overshooting conversions.
- // These are restricted to the following conversion:
- // a) A base class to a derived class reference
- // b) An lvalue-reference to an rvalue-reference
-
+ // Here we handle direct-initialization to a reference type as
+ // equivalent to a static_cast modulo overshooting conversions.
+ // These are restricted to the following conversions:
+ // a) A glvalue of a base class to a derived class reference
+ // b) An lvalue to an rvalue-reference of reference-compatible
+ // types
template<typename _Tp, typename _Arg>
struct __is_direct_constructible_ref_cast
: public __and_<__is_static_castable<_Arg, _Tp>,
__not_<__or_<__is_base_to_derived_ref<_Arg, _Tp>,
__is_lvalue_to_rvalue_ref<_Arg, _Tp>
- >>>::type::type
+ >>>::type
{ };
- // Direct-initialization is tricky, because of functional
- // casts: For a conversion to reference we fall back to a
- // static_cast modulo extra cases, otherwise we use a
- // new expression:
-
template<typename _Tp, typename _Arg>
struct __is_direct_constructible_new
: public conditional<is_reference<_Tp>::value,
@@ -802,9 +813,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Tp, typename _Arg>
struct __is_direct_constructible
: public integral_constant<bool, (__is_direct_constructible_new<
- _Tp, _Arg>::type::value)>
+ _Tp, _Arg>::value)>
{ };
+ // Since default-construction and binary direct-initialization have
+ // been handled separately, the implementation of the remaining
+ // n-ary construction cases is rather straightforward.
struct __do_is_nary_constructible_impl
{
template<typename _Tp, typename... _Args, typename
@@ -824,9 +838,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
template<typename _Tp, typename... _Args>
struct __is_nary_constructible
- : public __and_<is_destructible<_Tp>,
- __is_nary_constructible_impl<_Tp, _Args...>
- >::type::type
+ : public __is_nary_constructible_impl<_Tp, _Args...>::type
{
static_assert(sizeof...(_Args) > 1,
"Only useful for > 1 arguments");
diff --git a/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc b/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc
index af1522b..4fa005e 100644
--- a/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc
+++ b/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc
@@ -19,7 +19,7 @@
// with this library; see the file COPYING3. If not see
// <http://www.gnu.org/licenses/>.
-// { dg-error "static assertion failed" "" { target *-*-* } 1603 }
+// { dg-error "static assertion failed" "" { target *-*-* } 1615 }
#include <utility>
diff --git a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc
index 871bbe5..01a2068 100644
--- a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc
+++ b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc
@@ -48,5 +48,5 @@ void test01()
// { dg-error "instantiated from here" "" { target *-*-* } 40 }
// { dg-error "instantiated from here" "" { target *-*-* } 42 }
-// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1389 }
-// { dg-error "declaration of" "" { target *-*-* } 1353 }
+// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1401 }
+// { dg-error "declaration of" "" { target *-*-* } 1365 }
diff --git a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc
index edcce7c..7dd19d6 100644
--- a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc
+++ b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc
@@ -48,5 +48,5 @@ void test01()
// { dg-error "instantiated from here" "" { target *-*-* } 40 }
// { dg-error "instantiated from here" "" { target *-*-* } 42 }
-// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1313 }
-// { dg-error "declaration of" "" { target *-*-* } 1277 }
+// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1325 }
+// { dg-error "declaration of" "" { target *-*-* } 1289 }