[2.90.9] planning for the next release
scott snyder
snyder@d0sgibnl1.fnal.gov
Sat Apr 1 00:00:00 GMT 2000
> Yeah. This is actually going to be necessary, unfortunately. Thanks for
> this -- anything else? I'm not quite sure I have the test file I was
> using for your other bug anymore... perhaps you can just sync up with me
> and let me know what is outstanding? I thought you had two outstanding
> bugs. This was one of them. I'd like to get both resolved before I get to
> far into the libio merge. . .
I think that was the only I/O bug that i had reported that was still
outstanding -- at least that's the only one for which i still had a local
patch. Perhaps you were thinking of that problem of the string
extractors not setting failbit at EOF? I eventually did get a defect
report submitted for that, but a fix for it did get into cvs.
Anyway, here are the remaining libstdc++ patches i have in my local tree.
There's less commentary than i'd like, but it's getting late...
sss
=====================================================
1. There was some code in our system which was relying on being able
to output a double to a stream using operator<<, then read it
back in again with operator>> and get exactly the same value.
To do this, it was cranking the precision setting way up (i think
it set it to 30 or thereabouts). However, this was defeated
by the test in locale_facets which limited the precion to
numeric_limits<>::digits10 --- i think the value of digits10 may have
had the fractional part truncated, so it doesn't give quite enough
precision. I just allowed another few digits in the output -- shouldn't
do any harm.
2000-02-06 scott snyder <snyder@fnal.gov>
* bits/locale_facets.tcc (do_put): Allow a couple extra digits of
precision beyond that which we get from numeric_limits::digits10.
Index: bits/locale_facets.tcc
===================================================================
RCS file: /cvs/libstdc++/libstdc++/bits/locale_facets.tcc,v
retrieving revision 1.32
diff -u -p -r1.32 locale_facets.tcc
--- locale_facets.tcc 2000/03/21 06:24:04 1.32
+++ locale_facets.tcc 2000/03/29 06:19:05
@@ -1194,7 +1194,7 @@ namespace std
num_put<_CharT, _OutIter>::
do_put(iter_type __s, ios_base& __io, char_type __fill, double __v) const
{
- const streamsize __max_prec = numeric_limits<double>::digits10;
+ const streamsize __max_prec = numeric_limits<double>::digits10 + 3;
streamsize __prec = __io.precision();
// Protect against sprintf() buffer overflows.
if (__prec > __max_prec)
=====================================================
2. The current cvs version of g++ miscompiles the max() and min()
template functions in libstdc++.
Here's an example, tested on an i686-linux platform.
-----------------------------------------
extern "C" int printf (...);
template <class T>
const T& max (const T& a, const T& b)
{
return (a > b) ? a : b;
}
int main ()
{
const int& x = max (1, 2);
const int& y = max (3, 4);
printf ("%d\n", x);
}
-----------------------------------------
I get the output
$ g++ -o x x.cc
$ ./x
4
If one looks at the generated code, it seems that what's happening
in max() is that the inputs get copied to stack temporaries,
and the reference returned is actually a reference to one of these
temporaries --- which, of course, becomes invalid after max() returns.
This seems to occur due to the following in cp/call.c:build_conditional_expr:
/* Convert from reference types to ordinary types; no expressions
really have reference type in C++. */
arg2 = convert_from_reference (arg2);
arg3 = convert_from_reference (arg3);
At one point, i had managed to convince myself that the definition of
max() as above was actually incorrect according to the standard,
but just now, i can't seem to find the justification for that statement.
The definitions of max() and min() in libstdc++ are of the same form
as max() above, so they get bitten by this behavior. This can be
avoided by rewriting them to avoid using a conditional expression:
2000-02-25 scott snyder <snyder@fnal.gov>
* stl/bits/stl_algobase.h (max, min): Don't use comparison
operator.
Index: stl/bits/stl_algobase.h
===================================================================
RCS file: /cvs/libstdc++/libstdc++/stl/bits/stl_algobase.h,v
retrieving revision 1.13
diff -u -p -r1.13 stl_algobase.h
--- stl_algobase.h 2000/02/04 23:52:47 1.13
+++ stl_algobase.h 2000/03/29 06:42:45
@@ -85,24 +85,28 @@ inline void swap(_Tp& __a, _Tp& __b) {
template <class _Tp>
inline const _Tp& min(const _Tp& __a, const _Tp& __b) {
- return __b < __a ? __b : __a;
+ //return __b < __a ? __b : __a;
+ if (__b < __a) return __b; return __a;
}
template <class _Tp>
inline const _Tp& max(const _Tp& __a, const _Tp& __b) {
- return __a < __b ? __b : __a;
+ //return __a < __b ? __b : __a;
+ if (__a < __b) return __b; return __a;
}
#endif /* __BORLANDC__ */
template <class _Tp, class _Compare>
inline const _Tp& min(const _Tp& __a, const _Tp& __b, _Compare __comp) {
- return __comp(__b, __a) ? __b : __a;
+ //return __comp(__b, __a) ? __b : __a;
+ if (__comp(__b, __a)) return __b; return __a;
}
template <class _Tp, class _Compare>
inline const _Tp& max(const _Tp& __a, const _Tp& __b, _Compare __comp) {
- return __comp(__a, __b) ? __b : __a;
+ //return __comp(__a, __b) ? __b : __a;
+ if (__comp(__a, __b)) return __b; return __a;
}
//--------------------------------------------------
=====================================================
3. The test ios_manip_fmtflags.cc also didn't run correctly with
the cvs version of g++. The code was passing a temporary
to imbue(); the data structures owned by this temporary locale
were getting deleted when the temporary locale was deleted,
resulting in references to freed memory when the locale
was later used. I redid this to avoid the temporary:
2000-03-06 scott snyder <snyder@fnal.gov>
* testsuite/27_io/ios_manip_fmtflags.cc (test01): Don't give a
temporary to imbue().
Index: testsuite/27_io/ios_manip_fmtflags.cc
===================================================================
RCS file: /cvs/libstdc++/libstdc++/testsuite/27_io/ios_manip_fmtflags.cc,v
retrieving revision 1.1
diff -u -p -r1.1 ios_manip_fmtflags.cc
--- ios_manip_fmtflags.cc 1999/09/21 02:20:37 1.1
+++ ios_manip_fmtflags.cc 2000/03/29 06:44:27
@@ -57,7 +57,8 @@ void test01()
std::cout << ":" << std::setw(3) << std::left << true << ":" << std::endl;
std::cout << ":" << std::setw(3) << std::right << false << ":" << std::endl;
- std::cout.imbue(std::locale(std::locale(), new MyNP));
+ std::locale loc = std::locale (std::locale(), new MyNP);
+ std::cout.imbue(loc);
std::cout << std::boolalpha;
std::cout << true << " " << false << std::endl;
=====================================================
4. bitset_shift.cc was also giving compilation errors.
I haven't tested this recently to see if this is still a problem, though.
Index: testsuite/23_containers/bitset_shift.cc
===================================================================
RCS file: /cvs/libstdc++/libstdc++/testsuite/23_containers/bitset_shift.cc,v
retrieving revision 1.1
diff -u -p -r1.1 bitset_shift.cc
--- bitset_shift.cc 2000/01/31 21:20:22 1.1
+++ bitset_shift.cc 2000/03/29 06:52:12
@@ -68,19 +68,22 @@ template <size_t size>
initialise(size);
- std::bitset<size> original = std::string(original_bits);
+ //std::bitset<size> original = std::string(original_bits);
+ std::bitset<size> original = std::bitset<size> (std::string(original_bits));
for (size_t shift_step=0; shift_step==0 || shift_step<size; shift_step++) {
shift_arrays(shift_step, size);
shifted = original;
shifted <<= shift_step;
- correct = std::string(left_shifted);
+ //correct = std::string(left_shifted);
+ correct = std::bitset<size> (std::string(left_shifted));
test &= shifted == correct;
shifted = original;
shifted >>= shift_step;
- correct = std::string(right_shifted);
+ //correct = std::string(right_shifted);
+ correct = std::bitset<size> (std::string(right_shifted));
test &= shifted == correct;
}
=====================================================
5. Two more remarks:
- The cvs version of g++ has a bug that will cause it to build
a bad shared library on linux if it is generating code for i686.
Using -mpentium or lower avoids this bug. I reported this
a little while ago, and i think it is understood how to fix
it, but it hasn't been implemented yet. In the meantime,
i've patched src/Makefile.in to force -mpentium for my compiles.
- I also patch mkcheck.in to turn off optimization when compiling
the tests, since g++ is too unstable at the moment for that.
hope this helps,
sss
More information about the Libstdc++
mailing list