summaryrefslogtreecommitdiff
path: root/libstdc++-v3
diff options
context:
space:
mode:
authorJonathan Wakely <jwakely@redhat.com>2018-07-02 23:09:25 +0100
committerJonathan Wakely <redi@gcc.gnu.org>2018-07-02 23:09:25 +0100
commit8df27fcb9168fe26a6bcd34f4e653e1585895354 (patch)
treeb28afa0e0becf9af2fcb5fbaa355958c39549d58 /libstdc++-v3
parenta5eae716f66322842da21c17002c66b10c6f6b40 (diff)
downloadgcc-8df27fcb9168fe26a6bcd34f4e653e1585895354.tar.gz
P0758R1 Implicit conversion traits
Extend __is_convertible_helper to also detect whether the conversion is non-throwing, for std::is_nothrow_convertible in C++2a, * include/std/type_traits [__cplusplus > 201703] (__is_convertible_helper::__is_nothrow_type): Define new member. (__is_convertible_helper<_From, _To, false>::__test_aux1): Add noexcept. (__is_convertible_helper<_From, _To, false>::__test_nothrow) (__is_convertible_helper<_From, _To, false>::__is_nothrow_type): Add new members. (is_nothrow_convertible, is_nothrow_convertible_v): Define for C++2a. * testsuite/20_util/is_nothrow_convertible/value.cc: New. * testsuite/20_util/is_nothrow_convertible/requirements/ explicit_instantiation.cc: New. * testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc: New. From-SVN: r262322
Diffstat (limited to 'libstdc++-v3')
-rw-r--r--libstdc++-v3/ChangeLog15
-rw-r--r--libstdc++-v3/include/std/type_traits38
-rw-r--r--libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/explicit_instantiation.cc29
-rw-r--r--libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc33
-rw-r--r--libstdc++-v3/testsuite/20_util/is_nothrow_convertible/value.cc177
-rw-r--r--libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc2
-rw-r--r--libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc2
7 files changed, 291 insertions, 5 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog
index c6e84be4602..ae734e8487d 100644
--- a/libstdc++-v3/ChangeLog
+++ b/libstdc++-v3/ChangeLog
@@ -1,5 +1,20 @@
2018-07-02 Jonathan Wakely <jwakely@redhat.com>
+ P0758R1 Implicit conversion traits
+ * include/std/type_traits [__cplusplus > 201703]
+ (__is_convertible_helper::__is_nothrow_type): Define new member.
+ (__is_convertible_helper<_From, _To, false>::__test_aux1): Add
+ noexcept.
+ (__is_convertible_helper<_From, _To, false>::__test_nothrow)
+ (__is_convertible_helper<_From, _To, false>::__is_nothrow_type): Add
+ new members.
+ (is_nothrow_convertible, is_nothrow_convertible_v): Define for C++2a.
+ * testsuite/20_util/is_nothrow_convertible/value.cc: New.
+ * testsuite/20_util/is_nothrow_convertible/requirements/
+ explicit_instantiation.cc: New.
+ * testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc:
+ New.
+
P0887R1 The identity metafunction
* include/std/type_traits (type_identity, type_identity_t): Define
for C++2a.
diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits
index b2d3380f024..accea6df648 100644
--- a/libstdc++-v3/include/std/type_traits
+++ b/libstdc++-v3/include/std/type_traits
@@ -1341,13 +1341,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
bool = __or_<is_void<_From>, is_function<_To>,
is_array<_To>>::value>
struct __is_convertible_helper
- { typedef typename is_void<_To>::type type; };
+ {
+ typedef typename is_void<_To>::type type;
+#if __cplusplus > 201703L
+ typedef type __is_nothrow_type;
+#endif
+ };
template<typename _From, typename _To>
class __is_convertible_helper<_From, _To, false>
{
- template<typename _To1>
- static void __test_aux(_To1);
+ template<typename _To1>
+ static void __test_aux(_To1) noexcept;
template<typename _From1, typename _To1,
typename = decltype(__test_aux<_To1>(std::declval<_From1>()))>
@@ -1358,8 +1363,23 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
static false_type
__test(...);
+#if __cplusplus > 201703L
+ template<typename _From1, typename _To1,
+ bool _NoEx = noexcept(__test_aux<_To1>(std::declval<_From1>()))>
+ static __bool_constant<_NoEx>
+ __test_nothrow(int);
+
+ template<typename, typename>
+ static false_type
+ __test_nothrow(...);
+#endif
+
public:
typedef decltype(__test<_From, _To>(0)) type;
+
+#if __cplusplus > 201703L
+ typedef decltype(__test_nothrow<_From, _To>(0)) __is_nothrow_type;
+#endif
};
@@ -1369,6 +1389,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
: public __is_convertible_helper<_From, _To>::type
{ };
+#if __cplusplus > 201703L
+ /// is_nothrow_convertible
+ template<typename _From, typename _To>
+ struct is_nothrow_convertible
+ : public __is_convertible_helper<_From, _To>::__is_nothrow_type
+ { };
+
+ /// is_nothrow_convertible_v
+ template<typename _From, typename _To>
+ inline constexpr bool is_nothrow_convertible_v
+ = is_nothrow_convertible<_From, _To>::value;
+#endif // C++2a
// Const-volatile modifications.
diff --git a/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/explicit_instantiation.cc b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/explicit_instantiation.cc
new file mode 100644
index 00000000000..68f1adecb38
--- /dev/null
+++ b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/explicit_instantiation.cc
@@ -0,0 +1,29 @@
+// Copyright (C) 2018 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++2a" }
+// { dg-do compile { target c++2a } }
+
+// NB: This file is for testing type_traits with NO OTHER INCLUDES.
+
+#include <type_traits>
+
+namespace std
+{
+ typedef short test_type;
+ template struct is_nothrow_convertible<test_type, test_type>;
+}
diff --git a/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc
new file mode 100644
index 00000000000..3b5c6d51fe1
--- /dev/null
+++ b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/requirements/typedefs.cc
@@ -0,0 +1,33 @@
+// Copyright (C) 2018 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++2a" }
+// { dg-do compile { target c++2a } }
+
+// NB: This file is for testing type_traits with NO OTHER INCLUDES.
+
+#include <type_traits>
+
+void test01()
+{
+ // Check for required typedefs
+ typedef std::is_nothrow_convertible<int, int> test_type;
+ typedef test_type::value_type value_type;
+ typedef test_type::type type;
+ typedef test_type::type::value_type type_value_type;
+ typedef test_type::type::type type_type;
+}
diff --git a/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/value.cc b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/value.cc
new file mode 100644
index 00000000000..5824be4810d
--- /dev/null
+++ b/libstdc++-v3/testsuite/20_util/is_nothrow_convertible/value.cc
@@ -0,0 +1,177 @@
+// Copyright (C) 2018 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++2a" }
+// { dg-do compile { target c++2a } }
+
+#include <type_traits>
+#include <testsuite_tr1.h>
+
+void test01()
+{
+ using std::is_nothrow_convertible;
+ using namespace __gnu_test;
+
+ // Positive conversion tests.
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, const int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ volatile int, const int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, float>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ double, float>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float, int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int*, const int*>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int*, void*>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int[4], int*>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float&, int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, const int&>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const int&, int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float, const int&>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(int), int(*)(int)>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(&)(int), int(*)(int)>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ EnumType, int>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ClassType, ClassType>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ DerivedType, ClassType>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ DerivedType*, ClassType*>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ DerivedType&, ClassType&>(true));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ const int, const int&>(true));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ void, void>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const void, void>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ void, volatile void>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ double&, NoexceptExplicitClass>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ NoexceptCopyConsClass,
+ NoexceptCopyConsClass>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const NoexceptCopyConsClass,
+ NoexceptCopyConsClass>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const NoexceptCopyConsClass&,
+ NoexceptCopyConsClass>(true));
+ static_assert(test_relationship<is_nothrow_convertible,
+ NoexceptMoveConsClass,
+ NoexceptMoveConsClass>(true));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(int), int(&)(int)>(true));
+
+ // Negative conversion tests.
+ static_assert(test_relationship<is_nothrow_convertible,
+ const int*, int*>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int*, float*>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const int[4], int*>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int[4], int[4]>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const int&, int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float&, int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float, volatile int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(int), int(int)>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(int), int(*)(void)>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int(*)(int), int(&)(int)>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, EnumType>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, ClassType>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ClassType, DerivedType>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ClassType*, DerivedType*>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ClassType&, DerivedType&>(false));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ void, int>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ void, float>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ void, int(*)(int)>(false));
+
+ // C++0x
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, void>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int[4], void>(false));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ int, int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ float, volatile float&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const volatile int,
+ const volatile int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ volatile int, volatile int&>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ double&, ExplicitClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ int&, ExplicitClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ void*, ExplicitClass>(false));
+
+ static_assert(test_relationship<is_nothrow_convertible,
+ ExceptCopyConsClass,
+ ExceptCopyConsClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const ExceptCopyConsClass,
+ ExceptCopyConsClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ const ExceptCopyConsClass&,
+ ExceptCopyConsClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ExceptMoveConsClass,
+ ExceptMoveConsClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ ExceptMoveConsClass&,
+ ExceptMoveConsClass>(false));
+ static_assert(test_relationship<is_nothrow_convertible,
+ NoexceptMoveConsClass&,
+ NoexceptMoveConsClass>(false));
+}
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 13bca19c7e0..1380fc55c82 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
@@ -47,4 +47,4 @@ void test01()
// { dg-error "required from here" "" { target *-*-* } 39 }
// { dg-error "required from here" "" { target *-*-* } 41 }
-// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1793 }
+// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1825 }
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 9df01550ea3..cbc5300c182 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
@@ -47,5 +47,5 @@ void test01()
// { dg-error "required from here" "" { target *-*-* } 39 }
// { dg-error "required from here" "" { target *-*-* } 41 }
-// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1676 }
+// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1708 }