This is the mail archive of the
libstdc++@gcc.gnu.org
mailing list for the libstdc++ project.
Corrected patch for libstdc++/4354
- To: libstdc++ at gcc dot gnu dot org
- Subject: Corrected patch for libstdc++/4354
- From: Paolo Carlini <pcarlini at unitus dot it>
- Date: Sun, 23 Sep 2001 17:11:08 +0200
- CC: bkoz at redhat dot com, pme at gcc dot gnu dot org, bagnara at cs dot unipr dot it
- Organization: Universita' della Tuscia
- Reply-To: pcarlini at unitus dot it
Hi again,
I hope you will forgive me my very slow progress toward a working
solution: this is my first patch to gcc/libstdc++!
The fact is, my previous attempts were badly wrong.
I did'nt completely understand the reference counting issues in
_M_mutate and therefore I wrongly proposed a solution calling
_M_copy_chars *before* _M_mutate: this is not correct every time the
string is shared. In fact my patches badly broken the string class :( as
revealed by any simple test adding to Roberto's a string bux initialized
at the beginning as = aux, which became corrupted as an unwanted effect
of the aux.assign.
Now I believe that perhaps there is no simple escape to temporarily
copying the source data in a temporary string (we could avoid this if we
were sure that destination != source). Therefore the following patch is
my current proposal, which survives a make check and all the variants of
Roberto's testcase I could think of (also involving shared copies of
aux, of course)
Cheers,
Paolo.
--- basic_string.tcc.orig Sun Sep 23 16:56:21 2001
+++ basic_string.tcc Sun Sep 23 17:00:11 2001
@@ -453,10 +453,14 @@
if (__dmax <= __dnew)
__throw_length_error("basic_string::_M_replace");
size_type __off = __i1 - _M_ibegin();
+ // Save concerned source string data in a temporary
+ const basic_string __temp = string(__k1, __k2);
_M_mutate(__off, __dold, __dnew);
- // Invalidated __i1, __i2
+ // Invalidated __i1, __i2 (and clobbered original source string
+ // data when destination string == source string and the string
+ // is unshared)
if (__dnew)
- _S_copy_chars(_M_data() + __off, __k1, __k2);
+ _S_copy_chars(_M_data() + __off, __temp.begin(),
__temp.end());
return *this;
}