Don't report spurious errors from wxSocket in "no wait" mode.

In wxSOCKET_NOWAIT mode wxSOCKET_WOULDBLOCK is not a real error as it's
expected and should be just discarded. Failing to do this could result in the
following scenario:

1. Try to read a big buffer with wxSOCKET_NOWAIT (setting wxSocket error to
   wxSOCKET_WOULDBLOCK).
2. Process small part of it.
3. Read more data from wxSocket -- which now goes to the data containing
   already cached data without going to the socket itself and this without
   resetting the error.
4. Check wxSocket::Error() which turns out to be (still) true.

And this was exactly what happened in mysteriously failing unit test case
reading wxImage contents from a socket: the failure was difficult to reproduce
because it depended on how much data exactly did we read from the socket in
one go.

Fix this by resetting the error properly and reenable the unit test which was
previously disabled for the build bot, it should pass now.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@65378 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Vadim Zeitlin 2010-08-21 23:33:40 +00:00
parent 2dd62dc008
commit 686d0cc0a6
2 changed files with 22 additions and 14 deletions

View File

@ -980,7 +980,11 @@ wxUint32 wxSocketBase::DoRead(void* buffer_, wxUint32 nbytes)
{
// if we don't want to wait, just return immediately
if ( m_flags & wxSOCKET_NOWAIT )
{
// this shouldn't be counted as an error in this case
SetError(wxSOCKET_NOERROR);
break;
}
// otherwise wait until the socket becomes ready for reading or
// an error occurs on it

View File

@ -110,15 +110,6 @@ void ImageTestCase::LoadFromFile()
void ImageTestCase::LoadFromSocketStream()
{
// Skip this test when running on a build slave because it just keeps
// failing erratically and sends build failure notifications when it does.
//
// Of course, it would be even better to understand why does it fail but so
// far we didn't manage to do it so disable until someone can find the
// problem.
if ( wxGetUserId().Lower().Matches("buildslave*") )
return;
if (!IsNetworkAvailable()) // implemented in test.cpp
{
wxLogWarning("No network connectivity; skipping the "
@ -131,24 +122,37 @@ void ImageTestCase::LoadFromSocketStream()
wxBitmapType type;
} testData[] =
{
{ "http://wxwidgets.org/logo9.jpg", wxBITMAP_TYPE_JPEG },
{ "http://wxwidgets.org/favicon.ico", wxBITMAP_TYPE_ICO }
{ "http://www.wxwidgets.org/logo9.jpg", wxBITMAP_TYPE_JPEG },
{ "http://www.wxwidgets.org/favicon.ico", wxBITMAP_TYPE_ICO }
};
for (unsigned int i=0; i<WXSIZEOF(testData); i++)
{
wxURL url(testData[i].url);
CPPUNIT_ASSERT(url.GetError() == wxURL_NOERR);
WX_ASSERT_EQUAL_MESSAGE
(
("Constructing URL \"%s\" failed.", testData[i].url),
wxURL_NOERR,
url.GetError()
);
wxInputStream *in_stream = url.GetInputStream();
CPPUNIT_ASSERT(in_stream && in_stream->IsOk());
WX_ASSERT_MESSAGE
(
("Opening URL \"%s\" failed.", testData[i].url),
in_stream && in_stream->IsOk()
);
wxImage img;
// NOTE: it's important to inform wxImage about the type of the image being
// loaded otherwise it will try to autodetect the format, but that
// requires a seekable stream!
CPPUNIT_ASSERT(img.LoadFile(*in_stream, testData[i].type));
WX_ASSERT_MESSAGE
(
("Loading image from \"%s\" failed.", testData[i].url),
img.LoadFile(*in_stream, testData[i].type)
);
delete in_stream;
}