diff options
author | jason <jason@138bc75d-0d04-0410-961f-82ee72b054a4> | 2009-08-01 02:26:42 +0000 |
---|---|---|
committer | jason <jason@138bc75d-0d04-0410-961f-82ee72b054a4> | 2009-08-01 02:26:42 +0000 |
commit | aaa6e1c2fb96586f142e1f9c053399872212910b (patch) | |
tree | 835681f433a68776c98b51aa17db749656db573d /libstdc++-v3 | |
parent | c7f0e2f230deaaee9f00d7759280aec42b820c6d (diff) | |
download | gcc-aaa6e1c2fb96586f142e1f9c053399872212910b.tar.gz |
* call.c (convert_class_to_reference): Binding an lvalue to an
rvalue reference is bad. If the user-defined conversion is bad,
set bad_p before merging conversions.
(maybe_handle_ref_bind): Don't push down bad_p.
(reference_binding): Binding an lvalue to an rvalue reference is bad.
(convert_like_real): Give a helpful error about binding lvalue
to rvalue reference.
(reference_related_p): No longer static.
* typeck.c (build_typed_address): New.
(build_static_cast_1): Add static_cast from lvalue to &&.
* cp-tree.h: Adjust.
* include/bits/move.h (forward): Implement as in N2835.
(move): Implement as in N2831.
* include/std/istream (rvalue stream operator>>): New.
* include/std/ostream (rvalue stream operator<<): New.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@150327 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'libstdc++-v3')
-rw-r--r-- | libstdc++-v3/ChangeLog | 9 | ||||
-rw-r--r-- | libstdc++-v3/include/bits/move.h | 27 | ||||
-rw-r--r-- | libstdc++-v3/include/std/istream | 21 | ||||
-rw-r--r-- | libstdc++-v3/include/std/ostream | 21 | ||||
-rw-r--r-- | libstdc++-v3/testsuite/27_io/rvalue_streams.cc | 43 |
5 files changed, 117 insertions, 4 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index eb8b0e727fe..19f3dd1e7f2 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,4 +1,13 @@ 2009-07-31 Jason Merrill <jason@redhat.com> + Douglas Gregor <doug.gregor@gmail.com> + + * include/bits/move.h (forward): Implement as in N2835. + (move): Implement as in N2831. + * include/std/istream (rvalue stream operator>>): New. + * include/std/ostream (rvalue stream operator<<): New. + * testsuite/27_io/rvalue_streams.cc: New. + +2009-07-31 Jason Merrill <jason@redhat.com> * include/bits/forward_list.h (splice_after): Use forward. (merge): Likewise. diff --git a/libstdc++-v3/include/bits/move.h b/libstdc++-v3/include/bits/move.h index 25773e13c48..d1da1e40ddf 100644 --- a/libstdc++-v3/include/bits/move.h +++ b/libstdc++-v3/include/bits/move.h @@ -46,12 +46,31 @@ _GLIBCXX_BEGIN_NAMESPACE(std) typedef _Tp type; }; - /// forward - template<typename _Tp> - inline _Tp&& + /// forward (as per N2835) + /// Forward lvalues as rvalues. + template <class _Tp> + inline typename enable_if<!is_lvalue_reference<_Tp>::value, _Tp&&>::type + forward(typename std::identity<_Tp>::type& __t) + { return static_cast<_Tp&&>(__t); } + + /// Forward rvalues as rvalues. + template <class _Tp> + inline typename enable_if<!is_lvalue_reference<_Tp>::value, _Tp&&>::type forward(typename std::identity<_Tp>::type&& __t) + { return static_cast<_Tp&&>(__t); } + + // Forward lvalues as lvalues. + template <class _Tp> + inline typename enable_if<is_lvalue_reference<_Tp>::value, _Tp>::type + forward(typename std::identity<_Tp>::type __t) { return __t; } + // Prevent forwarding rvalues as const lvalues. + template <class _Tp> + inline typename enable_if<is_lvalue_reference<_Tp>::value, _Tp>::type + forward(typename std::remove_reference<_Tp>::type&& __t) + = delete; + /** * @brief Move a value. * @ingroup mutating_algorithms @@ -61,7 +80,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std) template<typename _Tp> inline typename std::remove_reference<_Tp>::type&& move(_Tp&& __t) - { return __t; } + { return static_cast<typename std::remove_reference<_Tp>::type&&>(__t); } _GLIBCXX_END_NAMESPACE diff --git a/libstdc++-v3/include/std/istream b/libstdc++-v3/include/std/istream index 1979a51327f..f20b8962539 100644 --- a/libstdc++-v3/include/std/istream +++ b/libstdc++-v3/include/std/istream @@ -827,6 +827,27 @@ _GLIBCXX_BEGIN_NAMESPACE(std) basic_istream<_CharT, _Traits>& ws(basic_istream<_CharT, _Traits>& __is); +#ifdef __GXX_EXPERIMENTAL_CXX0X__ + // [27.7.1.6] Rvalue stream extraction + /** + * @brief Generic extractor for rvalue stream + * @param is An input stream. + * @param x A reference to the extraction target. + * @return is + * + * This is just a forwarding function to allow extraction from + * rvalue streams since they won't bind to the extractor functions + * that take an lvalue reference. + */ + template<typename _CharT, typename _Traits, typename _Tp> + basic_istream<_CharT, _Traits>& + operator>>(basic_istream<_CharT, _Traits>&& __is, _Tp& __x) + { + __is >> __x; + return __is; + } +#endif // __GXX_EXPERIMENTAL_CXX0X__ + _GLIBCXX_END_NAMESPACE #ifndef _GLIBCXX_EXPORT_TEMPLATE diff --git a/libstdc++-v3/include/std/ostream b/libstdc++-v3/include/std/ostream index b9ea4a8ce19..136c3d62fba 100644 --- a/libstdc++-v3/include/std/ostream +++ b/libstdc++-v3/include/std/ostream @@ -562,6 +562,27 @@ _GLIBCXX_BEGIN_NAMESPACE(std) flush(basic_ostream<_CharT, _Traits>& __os) { return __os.flush(); } +#ifdef __GXX_EXPERIMENTAL_CXX0X__ + // [27.7.2.9] Rvalue stream insertion + /** + * @brief Generic inserter for rvalue stream + * @param os An input stream. + * @param x A reference to the object being inserted. + * @return os + * + * This is just a forwarding function to allow insertion to + * rvalue streams since they won't bind to the inserter functions + * that take an lvalue reference. + */ + template<typename _CharT, typename _Traits, typename _Tp> + basic_ostream<_CharT, _Traits>& + operator<<(basic_ostream<_CharT, _Traits>&& __os, const _Tp& __x) + { + __os << __x; + return __os; + } +#endif // __GXX_EXPERIMENTAL_CXX0X__ + _GLIBCXX_END_NAMESPACE #ifndef _GLIBCXX_EXPORT_TEMPLATE diff --git a/libstdc++-v3/testsuite/27_io/rvalue_streams.cc b/libstdc++-v3/testsuite/27_io/rvalue_streams.cc new file mode 100644 index 00000000000..b3cc630edc0 --- /dev/null +++ b/libstdc++-v3/testsuite/27_io/rvalue_streams.cc @@ -0,0 +1,43 @@ +// Copyright (C) 2008 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 2, 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 COPYING. If not, write to the Free +// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, +// USA. + +// { dg-do run } + +#include <sstream> +#include <string> +#include <testsuite_hooks.h> + +void +test01() +{ + int i = 1742; + // This usage isn't supported by the current draft. + // std::string result = (std::ostringstream() << i).str(); + std::ostringstream() << i; + std::string result ("1742"); + int i2; + std::istringstream(result) >> i2; + VERIFY (i == i2); +} + +int +main() +{ + test01(); + return 0; +} |