std::uninitialized_copy tries to test assignability as follows:
is_assignable<_ValueType1, _RefType>::value This is the wrong way around. For example, when the iterators are char*, this ends up as is_assignable<char, char&>::value which is false. It should be is_assignable<char&, char>::value which is true. The result is that uninitialized_copy needlessly picks the slow implementation. Trivial fix attached. (No tests ran because I'm getting "runtest: command not found" errors that I don't know how to fix.)
Index: libstdc++-v3/include/bits/stl_uninitialized.h =================================================================== --- libstdc++-v3/include/bits/stl_uninitialized.h (revision 219070) +++ libstdc++-v3/include/bits/stl_uninitialized.h (working copy) @@ -105,29 +105,29 @@ template<typename _InputIterator, typename _ForwardIterator> inline _ForwardIterator uninitialized_copy(_InputIterator __first, _InputIterator __last, _ForwardIterator __result) { typedef typename iterator_traits<_InputIterator>::value_type _ValueType1; typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType2; #if __cplusplus < 201103L const bool __assignable = true; #else // trivial types can have deleted assignment typedef typename iterator_traits<_InputIterator>::reference _RefType; - const bool __assignable = is_assignable<_ValueType1, _RefType>::value; + const bool __assignable = is_assignable<_RefType, _ValueType1>::value; #endif return std::__uninitialized_copy<__is_trivial(_ValueType1) && __is_trivial(_ValueType2) && __assignable>:: __uninit_copy(__first, __last, __result); } template<bool _TrivialValueType> struct __uninitialized_fill { template<typename _ForwardIterator, typename _Tp> static void