aboutsummaryrefslogtreecommitdiff
path: root/libstdc++-v3/src
diff options
context:
space:
mode:
authorJonathan Wakely <jwakely@redhat.com>2020-06-11 18:41:37 +0100
committerJonathan Wakely <jwakely@redhat.com>2020-06-11 18:41:37 +0100
commitb32eea9c0c25a03e77170675abc4e4bcab6d2b3b (patch)
tree9763a78fcc4c3eb8903f96ce5654a1b23752b8b3 /libstdc++-v3/src
parent8f896fe5cd5fd7162d2996d0c28a6e4647597c2b (diff)
downloadgcc-b32eea9c0c25a03e77170675abc4e4bcab6d2b3b.zip
gcc-b32eea9c0c25a03e77170675abc4e4bcab6d2b3b.tar.gz
gcc-b32eea9c0c25a03e77170675abc4e4bcab6d2b3b.tar.bz2
libstdc++: Fix istream::ignore discarding too many chars (PR 94749)
The current code assumes that if the next character in the stream is equal to the delimiter then we stopped because we saw that delimiter, and so discards it. But in the testcase for the PR we stop because we reached the maximum number of characters, and it's coincidence that the next character equals the delimiter. We should not discard the next character in that case. The fix is to check that we haven't discarded __n characters already, instead of checking whether the next character equals __delim. Because we've already checked for EOF, if we haven't discarded __n yet then we know we stopped because we saw the delimiter. On the other hand, if the next character is the delimiter we don't know if that's why we stopped. PR libstdc++/94749 * include/bits/istream.tcc (basic_istream::ignore(streamsize, CharT)): Only discard an extra character if we didn't already reach the maximum number. * src/c++98/istream.cc (istream::ignore(streamsiz, char)) (wistream::ignore(streamsize, wchar_t)): Likewise. * testsuite/27_io/basic_istream/ignore/char/94749.cc: New test. * testsuite/27_io/basic_istream/ignore/wchar_t/94749.cc: New test.
Diffstat (limited to 'libstdc++-v3/src')
-rw-r--r--libstdc++-v3/src/c++98/istream.cc12
1 files changed, 4 insertions, 8 deletions
diff --git a/libstdc++-v3/src/c++98/istream.cc b/libstdc++-v3/src/c++98/istream.cc
index 79d829e..d6fee1a 100644
--- a/libstdc++-v3/src/c++98/istream.cc
+++ b/libstdc++-v3/src/c++98/istream.cc
@@ -171,11 +171,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
if (traits_type::eq_int_type(__c, __eof))
__err |= ios_base::eofbit;
- else if (traits_type::eq_int_type(__c, __delim))
+ else if (_M_gcount < __n) // implies __c == __delim
{
- if (_M_gcount
- < __gnu_cxx::__numeric_traits<streamsize>::__max)
- ++_M_gcount;
+ ++_M_gcount;
__sb->sbumpc();
}
}
@@ -413,11 +411,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
if (traits_type::eq_int_type(__c, __eof))
__err |= ios_base::eofbit;
- else if (traits_type::eq_int_type(__c, __delim))
+ else if (_M_gcount < __n) // implies __c == __delim
{
- if (_M_gcount
- < __gnu_cxx::__numeric_traits<streamsize>::__max)
- ++_M_gcount;
+ ++_M_gcount;
__sb->sbumpc();
}
}