Details
[Home]
Issue of the Implementation # S0735
Brief
num_get<>::do_get(bool) sets eofbit flag incorrectly when boolalpha == true
Detailed Description
The description of the function
iter_type do_get(iter_type in, iter_type end, ios_base& str, ios_base::iostate& err, bool& val) const
states the following for the case when
(str.flags() & ios_base::boolalpha) != 0 (22.2.2.1.2):
Therefore, the comparison of 'in' and 'end' iterators should take place if and only if the sequence read so far using (*in++) equals neither of the target sequences (returned by truename() and falsename()) but may become equal in the future as more characters are read.
Particularly, assume truename() returns "true" and falsename() returns "false". Once 't', 'r', 'u', 'e' symbols have been read from the stream, there will be no further comparison of 'in' and 'end' even though 'in' may equal 'end' at the moment.
It follows from the above that the 'eofbit' flag is set if and only if 'in' happened to equal 'end' during the reading of the sequence from the stream. Note that this is not the same as if 'in' was equal to 'end' after the sequence has been read. The actual implementation, however, behaves in a different way. It sets the 'eofbit' flag if just before return from the function in == end. That is, the comparison takes place after the sequence has been read and matched (or not matched).
This results, for instance, in setting a wrong value of 'err' in the following examples given in the standard right after the description of do_get() function (22.2.2.1.2 p16):
For targets true: "1" and false: "0", the input sequence "1" yields val == true and err == str.goodbit. For empty targets (""), any input sequence yields err == str.failbit.In practice, the implementation sets err = str.eofbit in the first case and err = str.failbit | str.eofbit in the second one (when the stream is empty, that is, originally in == end).
The example below demonstrated the behaviour of the function when the strings "true" and "false" correspond to true and false, respectively and the input sequence is "true".
According to the standard, 'eofbit' flag should not be set but it is, actually.
Problem location(s) in the standard
Linux Standard Base C++ Specification 3.2, Chapter 9. Libraries, 9.1. Interfaces for libstdcxx that refers ISO/IEC 14882: 2003 Programming languages --C++, section 22.2.2.1.2
Example
#include <iostream> #include <sstream> using namespace std; int main() { istringstream is("true"); bool result; is >> boolalpha >> result; if(is.rdstate() & ios_base::eofbit) cout << "eofbit was set." << endl; else cout << "eofbit wasn't set." << endl; return 0; }
Component
libstdc++
Accepted
GCC Bugzilla 37958
Status
Fixed in gcc-4.4.0
[Home]