summaryrefslogtreecommitdiffstats
path: root/libcxx
diff options
context:
space:
mode:
authorHoward Hinnant <hhinnant@apple.com>2010-11-18 01:40:00 +0000
committerHoward Hinnant <hhinnant@apple.com>2010-11-18 01:40:00 +0000
commita4a1ef1fc265d0abd1534ff892aa91edd6cc8bd4 (patch)
tree5e41a303980c5b7669d88d4b5ed5701ced337a6f /libcxx
parent9c335bf977cd0593cfdeb0efc4c70a1cb67ab0d8 (diff)
downloadbcm5719-llvm-a4a1ef1fc265d0abd1534ff892aa91edd6cc8bd4.tar.gz
bcm5719-llvm-a4a1ef1fc265d0abd1534ff892aa91edd6cc8bd4.zip
LWG 1404
llvm-svn: 119609
Diffstat (limited to 'libcxx')
-rw-r--r--libcxx/include/memory33
-rw-r--r--libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/difference_type.pass.cpp24
-rw-r--r--libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/size_type.pass.cpp26
3 files changed, 72 insertions, 11 deletions
diff --git a/libcxx/include/memory b/libcxx/include/memory
index 2eb87c3b787..130613e2be4 100644
--- a/libcxx/include/memory
+++ b/libcxx/include/memory
@@ -52,8 +52,11 @@ struct allocator_traits
| pointer_traits<pointer>::rebind<const void>
const_void_pointer;
typedef Alloc::difference_type
- | ptrdiff_t difference_type;
- typedef Alloc::size_type | size_t size_type;
+ | pointer_traits<pointer>::difference_type
+ difference_type;
+ typedef Alloc::size_type
+ | make_unsigned<difference_type>::type
+ size_type;
typedef Alloc::propagate_on_container_copy_assignment
| false_type propagate_on_container_copy_assignment;
typedef Alloc::propagate_on_container_move_assignment
@@ -856,7 +859,7 @@ struct __pointer_type<_Tp, _Dp, false>
typedef _Tp* type;
};
-}
+} // __pointer_type_imp
template <class _Tp, class _Dp>
struct __pointer_type
@@ -972,14 +975,14 @@ public:
static const bool value = sizeof(__test<_Tp>(0)) == 1;
};
-template <class _Alloc, bool = __has_size_type<_Alloc>::value>
+template <class _Alloc, class _DiffType, bool = __has_size_type<_Alloc>::value>
struct __size_type
{
- typedef size_t type;
+ typedef typename make_unsigned<_DiffType>::type type;
};
-template <class _Alloc>
-struct __size_type<_Alloc, true>
+template <class _Alloc, class _DiffType>
+struct __size_type<_Alloc, _DiffType, true>
{
typedef typename _Alloc::size_type type;
};
@@ -1292,6 +1295,18 @@ struct __has_select_on_container_copy_construction
#endif // _LIBCPP_HAS_NO_ADVANCED_SFINAE
+template <class _Alloc, class _Ptr, bool = __has_difference_type<_Alloc>::value>
+struct __alloc_traits_difference_type
+{
+ typedef typename pointer_traits<_Ptr>::difference_type type;
+};
+
+template <class _Alloc, class _Ptr>
+struct __alloc_traits_difference_type<_Alloc, _Ptr, true>
+{
+ typedef typename _Alloc::difference_type type;
+};
+
template <class _Alloc>
struct _LIBCPP_VISIBLE allocator_traits
{
@@ -1303,8 +1318,8 @@ struct _LIBCPP_VISIBLE allocator_traits
typedef typename __void_pointer<pointer, allocator_type>::type void_pointer;
typedef typename __const_void_pointer<pointer, allocator_type>::type const_void_pointer;
- typedef typename __pointer_traits_difference_type<allocator_type>::type difference_type;
- typedef typename __size_type<allocator_type>::type size_type;
+ typedef typename __alloc_traits_difference_type<allocator_type, pointer>::type difference_type;
+ typedef typename __size_type<allocator_type, difference_type>::type size_type;
typedef typename __propagate_on_container_copy_assignment<allocator_type>::type
propagate_on_container_copy_assignment;
diff --git a/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/difference_type.pass.cpp b/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/difference_type.pass.cpp
index 62fd23f5637..085c911b070 100644
--- a/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/difference_type.pass.cpp
+++ b/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/difference_type.pass.cpp
@@ -13,7 +13,7 @@
// struct allocator_traits
// {
// typedef Alloc::difference_type
-// | ptrdiff_t difference_type;
+// | pointer_traits<pointer>::difference_type difference_type;
// ...
// };
@@ -33,8 +33,30 @@ struct B
typedef T value_type;
};
+template <class T>
+struct C
+{
+ typedef T value_type;
+ struct pointer {};
+ struct const_pointer {};
+ struct void_pointer {};
+ struct const_void_pointer {};
+};
+
+namespace std
+{
+
+template <>
+struct pointer_traits<C<char>::pointer>
+{
+ typedef signed char difference_type;
+};
+
+}
+
int main()
{
static_assert((std::is_same<std::allocator_traits<A<char> >::difference_type, short>::value), "");
static_assert((std::is_same<std::allocator_traits<B<char> >::difference_type, std::ptrdiff_t>::value), "");
+ static_assert((std::is_same<std::allocator_traits<C<char> >::difference_type, signed char>::value), "");
}
diff --git a/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/size_type.pass.cpp b/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/size_type.pass.cpp
index 7a6d7891751..e9c175fe86a 100644
--- a/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/size_type.pass.cpp
+++ b/libcxx/test/utilities/memory/allocator.traits/allocator.traits.types/size_type.pass.cpp
@@ -32,8 +32,32 @@ struct B
typedef T value_type;
};
+template <class T>
+struct C
+{
+ typedef T value_type;
+ struct pointer {};
+ struct const_pointer {};
+ struct void_pointer {};
+ struct const_void_pointer {};
+};
+
+namespace std
+{
+
+template <>
+struct pointer_traits<C<char>::pointer>
+{
+ typedef signed char difference_type;
+};
+
+}
+
int main()
{
static_assert((std::is_same<std::allocator_traits<A<char> >::size_type, unsigned short>::value), "");
- static_assert((std::is_same<std::allocator_traits<B<char> >::size_type, std::size_t>::value), "");
+ static_assert((std::is_same<std::allocator_traits<B<char> >::size_type,
+ std::make_unsigned<std::ptrdiff_t>::type>::value), "");
+ static_assert((std::is_same<std::allocator_traits<C<char> >::size_type,
+ unsigned char>::value), "");
}
OpenPOWER on IntegriCloud