This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[v3, v7-branch] Some work on basic_string & co
- From: Paolo Carlini <pcarlini at suse dot de>
- To: "'gcc-patches at gcc dot gnu dot org'" <gcc-patches at gcc dot gnu dot org>
- Date: Sun, 12 Jun 2005 22:48:41 +0200
- Subject: [v3, v7-branch] Some work on basic_string & co
Hi,
a grab bag of fixes and improvements. I'm becoming rather happy with the
code ;)
Tested x86-linux, --enable-libstdcxx-string=sso/rc.
Paolo.
//////////////////
2005-06-12 Paolo Carlini <pcarlini@suse.de>
* include/bits/basic_string.h (reserve): Forward to
_M_reserve.
(assign(const basic_string&)): Likewise to _M_assign.
* include/bits/basic_string.tcc (reserve,
assign(const basic_string&)): Remove.
* include/ext/rc_string.h (_M_reserve): Tweak consistently.
* include/ext/sso_string.h (_M_reserve): Likewise.
* include/ext/sso_string.h (_M_dispose): New, check
_M_is_local and forward to _M_destroy.
(_M_destroy): Adjust; adjust all callers to use _M_dispose.
(_M_reserve): Use _M_destroy.
* include/ext/sso_string.h: Rename _S_construct ->
_M_construct.
* src/sso_string-inst.cc: Likewise.
* src/allocator-inst.cc: Add instantiation for size_t.
* src/bitmap_allocator.cc: Likewise.
diff -prN libstdc++-v3-orig/include/bits/basic_string.h libstdc++-v3/include/bits/basic_string.h
*** libstdc++-v3-orig/include/bits/basic_string.h Sun Jun 5 14:22:31 2005
--- libstdc++-v3/include/bits/basic_string.h Sun Jun 12 19:32:56 2005
*************** namespace std
*** 414,420 ****
* data.
*/
void
! reserve(size_type __res_arg = 0);
/**
* Erases the string, making it empty.
--- 414,421 ----
* data.
*/
void
! reserve(size_type __res_arg = 0)
! { this->_M_reserve(__res_arg); }
/**
* Erases the string, making it empty.
*************** namespace std
*** 623,629 ****
* @return Reference to this string.
*/
basic_string&
! assign(const basic_string& __str);
/**
* @brief Set value to a substring of a string.
--- 624,634 ----
* @return Reference to this string.
*/
basic_string&
! assign(const basic_string& __str)
! {
! this->_M_assign(__str);
! return *this;
! }
/**
* @brief Set value to a substring of a string.
diff -prN libstdc++-v3-orig/include/bits/basic_string.tcc libstdc++-v3/include/bits/basic_string.tcc
*** libstdc++-v3-orig/include/bits/basic_string.tcc Sun Feb 20 16:45:53 2005
--- libstdc++-v3/include/bits/basic_string.tcc Sun Jun 12 17:16:24 2005
*************** namespace std
*** 54,68 ****
template<typename _CharT, typename _Traits, typename _Alloc>
basic_string<_CharT, _Traits, _Alloc>&
basic_string<_CharT, _Traits, _Alloc>::
- assign(const basic_string& __str)
- {
- this->_M_assign(__str);
- return *this;
- }
-
- template<typename _CharT, typename _Traits, typename _Alloc>
- basic_string<_CharT, _Traits, _Alloc>&
- basic_string<_CharT, _Traits, _Alloc>::
assign(const _CharT* __s, size_type __n)
{
__glibcxx_requires_string_len(__s, __n);
--- 54,59 ----
*************** namespace std
*** 229,248 ****
template<typename _CharT, typename _Traits, typename _Alloc>
void
basic_string<_CharT, _Traits, _Alloc>::
- reserve(size_type __res)
- {
- if (__res != this->capacity() || this->_M_is_shared())
- {
- // Make sure we don't shrink below the current size
- if (__res < this->size())
- __res = this->size();
- this->_M_reserve(__res);
- }
- }
-
- template<typename _CharT, typename _Traits, typename _Alloc>
- void
- basic_string<_CharT, _Traits, _Alloc>::
swap(basic_string& __s)
{
if (this->_M_is_leaked())
--- 220,225 ----
diff -prN libstdc++-v3-orig/include/ext/rc_string.h libstdc++-v3/include/ext/rc_string.h
*** libstdc++-v3-orig/include/ext/rc_string.h Sun Jun 5 14:22:43 2005
--- libstdc++-v3/include/ext/rc_string.h Sun Jun 12 19:30:48 2005
*************** namespace __gnu_cxx
*** 618,627 ****
__rc_string<_CharT, _Traits, _Alloc>::
_M_reserve(size_type __res)
{
! const allocator_type __a = _M_get_allocator();
! _CharT* __tmp = _M_rep()->_M_clone(__a, __res - _M_length());
! _M_dispose(__a);
! _M_data(__tmp);
}
template<typename _CharT, typename _Traits, typename _Alloc>
--- 618,634 ----
__rc_string<_CharT, _Traits, _Alloc>::
_M_reserve(size_type __res)
{
! if (__res != _M_capacity() || _M_is_shared())
! {
! // Make sure we don't shrink below the current size.
! if (__res < _M_length())
! __res = _M_length();
!
! const allocator_type __a = _M_get_allocator();
! _CharT* __tmp = _M_rep()->_M_clone(__a, __res - _M_length());
! _M_dispose(__a);
! _M_data(__tmp);
! }
}
template<typename _CharT, typename _Traits, typename _Alloc>
diff -prN libstdc++-v3-orig/include/ext/sso_string.h libstdc++-v3/include/ext/sso_string.h
*** libstdc++-v3-orig/include/ext/sso_string.h Sat Jun 11 10:27:55 2005
--- libstdc++-v3/include/ext/sso_string.h Sun Jun 12 22:14:22 2005
*************** namespace __gnu_cxx
*** 117,123 ****
_S_create(size_type&, size_type, const _Alloc&);
void
! _M_destroy(const _Alloc&) throw();
// Use empty-base optimization: http://www.cantrip.org/emptyopt.html
struct _Alloc_hider : _Alloc
--- 117,130 ----
_S_create(size_type&, size_type, const _Alloc&);
void
! _M_dispose(const _Alloc& __a) throw()
! {
! if (!_M_is_local())
! _M_destroy(__a, _M_allocated_capacity + 1);
! }
!
! void
! _M_destroy(const _Alloc&, size_type) throw();
// Use empty-base optimization: http://www.cantrip.org/emptyopt.html
struct _Alloc_hider : _Alloc
*************** namespace __gnu_cxx
*** 128,134 ****
_CharT* _M_p; // The actual data.
};
! // Data Member (private):
_Alloc_hider _M_dataplus;
size_type _M_string_length;
--- 135,141 ----
_CharT* _M_p; // The actual data.
};
! // Data Members (private):
_Alloc_hider _M_dataplus;
size_type _M_string_length;
*************** namespace __gnu_cxx
*** 152,194 ****
// requires special behaviour if _InIter is an integral type
template<class _InIterator>
void
! _S_construct_aux(_InIterator __beg, _InIterator __end,
const _Alloc& __a, __false_type)
{
typedef typename iterator_traits<_InIterator>::iterator_category _Tag;
! _S_construct(__beg, __end, __a, _Tag());
}
template<class _InIterator>
void
! _S_construct_aux(_InIterator __beg, _InIterator __end,
const _Alloc& __a, __true_type)
! { _S_construct(static_cast<size_type>(__beg),
static_cast<value_type>(__end), __a); }
template<class _InIterator>
void
! _S_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a)
{
typedef typename std::__is_integer<_InIterator>::__type _Integral;
! _S_construct_aux(__beg, __end, __a, _Integral());
}
// For Input Iterators, used in istreambuf_iterators, etc.
template<class _InIterator>
void
! _S_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::input_iterator_tag);
// For forward_iterators up to random_access_iterators, used for
// string::iterator, _CharT*, etc.
template<class _FwdIterator>
void
! _S_construct(_FwdIterator __beg, _FwdIterator __end, const _Alloc& __a,
std::forward_iterator_tag);
void
! _S_construct(size_type __req, _CharT __c, const _Alloc& __a);
public:
_CharT*
--- 159,201 ----
// requires special behaviour if _InIter is an integral type
template<class _InIterator>
void
! _M_construct_aux(_InIterator __beg, _InIterator __end,
const _Alloc& __a, __false_type)
{
typedef typename iterator_traits<_InIterator>::iterator_category _Tag;
! _M_construct(__beg, __end, __a, _Tag());
}
template<class _InIterator>
void
! _M_construct_aux(_InIterator __beg, _InIterator __end,
const _Alloc& __a, __true_type)
! { _M_construct(static_cast<size_type>(__beg),
static_cast<value_type>(__end), __a); }
template<class _InIterator>
void
! _M_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a)
{
typedef typename std::__is_integer<_InIterator>::__type _Integral;
! _M_construct_aux(__beg, __end, __a, _Integral());
}
// For Input Iterators, used in istreambuf_iterators, etc.
template<class _InIterator>
void
! _M_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::input_iterator_tag);
// For forward_iterators up to random_access_iterators, used for
// string::iterator, _CharT*, etc.
template<class _FwdIterator>
void
! _M_construct(_FwdIterator __beg, _FwdIterator __end, const _Alloc& __a,
std::forward_iterator_tag);
void
! _M_construct(size_type __req, _CharT __c, const _Alloc& __a);
public:
_CharT*
*************** namespace __gnu_cxx
*** 247,253 ****
const _Alloc& __a);
~__sso_string()
! { _M_destroy(_M_get_allocator()); }
allocator_type
_M_get_allocator() const
--- 254,260 ----
const _Alloc& __a);
~__sso_string()
! { _M_dispose(_M_get_allocator()); }
allocator_type
_M_get_allocator() const
*************** namespace __gnu_cxx
*** 269,274 ****
--- 276,287 ----
template<typename _CharT, typename _Traits, typename _Alloc>
void
__sso_string<_CharT, _Traits, _Alloc>::
+ _M_destroy(const _Alloc& __a, size_type __size) throw()
+ { _CharT_alloc_type(__a).deallocate(_M_data(), __size); }
+
+ template<typename _CharT, typename _Traits, typename _Alloc>
+ void
+ __sso_string<_CharT, _Traits, _Alloc>::
_M_swap(__sso_string& __rcs)
{
const bool __local = _M_is_local();
*************** namespace __gnu_cxx
*** 357,395 ****
}
template<typename _CharT, typename _Traits, typename _Alloc>
- void
- __sso_string<_CharT, _Traits, _Alloc>::
- _M_destroy(const _Alloc& __a) throw ()
- {
- if (!_M_is_local())
- _CharT_alloc_type(__a).deallocate(_M_data(), _M_allocated_capacity + 1);
- }
-
- template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _S_construct(size_type(), _CharT(), __a); }
template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(const __sso_string& __rcs)
: _M_dataplus(__rcs._M_get_allocator(), _M_local_data)
! { _S_construct(__rcs._M_data(), __rcs._M_data() + __rcs._M_length(),
__rcs._M_get_allocator()); }
template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(size_type __n, _CharT __c, const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _S_construct(__n, __c, __a); }
template<typename _CharT, typename _Traits, typename _Alloc>
template<typename _InputIterator>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(_InputIterator __beg, _InputIterator __end, const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _S_construct(__beg, __end, __a); }
// NB: This is the special case for Input Iterators, used in
// istreambuf_iterators, etc.
--- 370,399 ----
}
template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _M_construct(size_type(), _CharT(), __a); }
template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(const __sso_string& __rcs)
: _M_dataplus(__rcs._M_get_allocator(), _M_local_data)
! { _M_construct(__rcs._M_data(), __rcs._M_data() + __rcs._M_length(),
__rcs._M_get_allocator()); }
template<typename _CharT, typename _Traits, typename _Alloc>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(size_type __n, _CharT __c, const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _M_construct(__n, __c, __a); }
template<typename _CharT, typename _Traits, typename _Alloc>
template<typename _InputIterator>
__sso_string<_CharT, _Traits, _Alloc>::
__sso_string(_InputIterator __beg, _InputIterator __end, const _Alloc& __a)
: _M_dataplus(__a, _M_local_data)
! { _M_construct(__beg, __end, __a); }
// NB: This is the special case for Input Iterators, used in
// istreambuf_iterators, etc.
*************** namespace __gnu_cxx
*** 399,405 ****
template<typename _InIterator>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _S_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::input_iterator_tag)
{
// Avoid reallocation for common case.
--- 403,409 ----
template<typename _InIterator>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _M_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::input_iterator_tag)
{
// Avoid reallocation for common case.
*************** namespace __gnu_cxx
*** 422,428 ****
__capacity = __len + 1;
_CharT* __another = _S_create(__capacity, __len, __a);
_S_copy(__another, _M_data(), __len);
! _M_destroy(__a);
_M_data(__another);
_M_capacity(__capacity);
}
--- 426,432 ----
__capacity = __len + 1;
_CharT* __another = _S_create(__capacity, __len, __a);
_S_copy(__another, _M_data(), __len);
! _M_dispose(__a);
_M_data(__another);
_M_capacity(__capacity);
}
*************** namespace __gnu_cxx
*** 432,438 ****
}
catch(...)
{
! _M_destroy(__a);
__throw_exception_again;
}
--- 436,442 ----
}
catch(...)
{
! _M_dispose(__a);
__throw_exception_again;
}
*************** namespace __gnu_cxx
*** 443,449 ****
template <typename _InIterator>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _S_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::forward_iterator_tag)
{
// NB: Not required, but considered best practice.
--- 447,453 ----
template <typename _InIterator>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _M_construct(_InIterator __beg, _InIterator __end, const _Alloc& __a,
std::forward_iterator_tag)
{
// NB: Not required, but considered best practice.
*************** namespace __gnu_cxx
*** 464,470 ****
{ _S_copy_chars(_M_data(), __beg, __end); }
catch(...)
{
! _M_destroy(__a);
__throw_exception_again;
}
--- 468,474 ----
{ _S_copy_chars(_M_data(), __beg, __end); }
catch(...)
{
! _M_dispose(__a);
__throw_exception_again;
}
*************** namespace __gnu_cxx
*** 474,480 ****
template<typename _CharT, typename _Traits, typename _Alloc>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _S_construct(size_type __n, _CharT __c, const _Alloc& __a)
{
if (__n > size_type(_S_local_capacity))
{
--- 478,484 ----
template<typename _CharT, typename _Traits, typename _Alloc>
void
__sso_string<_CharT, _Traits, _Alloc>::
! _M_construct(size_type __n, _CharT __c, const _Alloc& __a)
{
if (__n > size_type(_S_local_capacity))
{
*************** namespace __gnu_cxx
*** 502,508 ****
if (__size > size_type(_S_local_capacity))
__tmp = _S_create(__size, size_type(0), __a);
! _M_destroy(__a);
_M_data(__tmp);
if (__size)
--- 506,512 ----
if (__size > size_type(_S_local_capacity))
__tmp = _S_create(__size, size_type(0), __a);
! _M_dispose(__a);
_M_data(__tmp);
if (__size)
*************** namespace __gnu_cxx
*** 521,549 ****
_M_reserve(size_type __res)
{
const size_type __capacity = _M_capacity();
! const allocator_type __a = _M_get_allocator();
!
! if (__res > __capacity
! || __res > size_type(_S_local_capacity))
{
! _CharT* __tmp = _S_create(__res, __capacity, __a);
! if (_M_length())
! _S_copy(__tmp, _M_data(), _M_length());
! _M_destroy(__a);
! _M_data(__tmp);
! _M_capacity(__res);
! }
! else if (!_M_is_local())
! {
! const size_type __tmp_capacity = _M_allocated_capacity;
! if (_M_length())
! _S_copy(_M_local_data, _M_data(), _M_length());
! // XXX
! _CharT_alloc_type(__a).deallocate(_M_data(), __tmp_capacity + 1);
! _M_data(_M_local_data);
! }
! _M_set_length(_M_length());
}
template<typename _CharT, typename _Traits, typename _Alloc>
--- 525,559 ----
_M_reserve(size_type __res)
{
const size_type __capacity = _M_capacity();
! if (__res != __capacity)
{
! const allocator_type __a = _M_get_allocator();
! // Make sure we don't shrink below the current size.
! if (__res < _M_length())
! __res = _M_length();
!
! if (__res > __capacity
! || __res > size_type(_S_local_capacity))
! {
! _CharT* __tmp = _S_create(__res, __capacity, __a);
! if (_M_length())
! _S_copy(__tmp, _M_data(), _M_length());
! _M_dispose(__a);
! _M_data(__tmp);
! _M_capacity(__res);
! }
! else if (!_M_is_local())
! {
! const size_type __tmp_capacity = _M_allocated_capacity;
! if (_M_length())
! _S_copy(_M_local_data, _M_data(), _M_length());
! _M_destroy(__a, __tmp_capacity + 1);
! _M_data(_M_local_data);
! }
!
! _M_set_length(_M_length());
! }
}
template<typename _CharT, typename _Traits, typename _Alloc>
*************** namespace __gnu_cxx
*** 568,574 ****
_S_copy(__r + __pos + __len2,
_M_data() + __pos + __len1, __how_much);
! _M_destroy(__a);
_M_data(__r);
_M_capacity(__new_capacity);
}
--- 578,584 ----
_S_copy(__r + __pos + __len2,
_M_data() + __pos + __len1, __how_much);
! _M_dispose(__a);
_M_data(__r);
_M_capacity(__new_capacity);
}
diff -prN libstdc++-v3-orig/src/allocator-inst.cc libstdc++-v3/src/allocator-inst.cc
*** libstdc++-v3-orig/src/allocator-inst.cc Thu Sep 16 14:14:13 2004
--- libstdc++-v3/src/allocator-inst.cc Sun Jun 12 20:52:10 2005
***************
*** 1,6 ****
// Explicit instantiation file.
! // Copyright (C) 1999, 2001, 2002, 2003, 2004 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
--- 1,7 ----
// Explicit instantiation file.
! // Copyright (C) 1999, 2001, 2002, 2003, 2004, 2005
! // 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
*************** namespace std
*** 37,40 ****
--- 38,42 ----
{
template class allocator<char>;
template class allocator<wchar_t>;
+ template class allocator<size_t>;
} // namespace std
diff -prN libstdc++-v3-orig/src/bitmap_allocator.cc libstdc++-v3/src/bitmap_allocator.cc
*** libstdc++-v3-orig/src/bitmap_allocator.cc Sun May 22 13:16:20 2005
--- libstdc++-v3/src/bitmap_allocator.cc Sun Jun 12 20:06:02 2005
*************** namespace __gnu_cxx
*** 128,131 ****
--- 128,132 ----
// Instantiations.
template class bitmap_allocator<char>;
template class bitmap_allocator<wchar_t>;
+ template class bitmap_allocator<size_t>;
} // namespace __gnu_cxx
diff -prN libstdc++-v3-orig/src/sso_string-inst.cc libstdc++-v3/src/sso_string-inst.cc
*** libstdc++-v3-orig/src/sso_string-inst.cc Fri Jun 10 22:49:28 2005
--- libstdc++-v3/src/sso_string-inst.cc Sun Jun 12 11:49:21 2005
*************** namespace __gnu_cxx
*** 60,75 ****
template
void
! RS::_S_construct(RS::iterator, RS::iterator,
const allocator<C>&, std::forward_iterator_tag);
template
void
! RS::_S_construct(C*, C*, const allocator<C>&,
std::forward_iterator_tag);
template
void
! RS::_S_construct(const C*, const C*, const allocator<C>&,
std::forward_iterator_tag);
} // namespace __gnu_cxx
--- 60,75 ----
template
void
! RS::_M_construct(RS::iterator, RS::iterator,
const allocator<C>&, std::forward_iterator_tag);
template
void
! RS::_M_construct(C*, C*, const allocator<C>&,
std::forward_iterator_tag);
template
void
! RS::_M_construct(const C*, const C*, const allocator<C>&,
std::forward_iterator_tag);
} // namespace __gnu_cxx