Skip to content

Commit f352a74

Browse files
authored
Fix HttpClient SendRequestAsync bugs (#976)
* potential fix potential fix * pr feedback * move to while loop * pr feedback * rename
1 parent 038a6e0 commit f352a74

File tree

1 file changed

+10
-9
lines changed

1 file changed

+10
-9
lines changed

lib/http/HttpClient_WinInet.cpp

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,9 @@ class WinInetRequestWrapper
3232
HINTERNET m_hWinInetRequest {nullptr};
3333
SimpleHttpRequest* m_request;
3434
BYTE m_buffer[1024] {0};
35+
DWORD m_bufferUsed {0};
36+
std::vector<uint8_t> m_bodyBuffer;
37+
bool m_readingData {false};
3538
bool isCallbackCalled {false};
3639
bool isAborted {false};
3740
public:
@@ -316,20 +319,15 @@ class WinInetRequestWrapper
316319

317320
void onRequestComplete(DWORD dwError)
318321
{
319-
std::unique_ptr<SimpleHttpResponse> response(new SimpleHttpResponse(m_id));
320-
321-
std::vector<uint8_t> & m_bodyBuffer = response->m_body;
322-
DWORD m_bufferUsed = 0;
323-
324322
if (dwError == ERROR_SUCCESS) {
325323
// If looking good so far, try to fetch the response body first.
326324
// It might potentially be another async operation which will
327325
// trigger INTERNET_STATUS_REQUEST_COMPLETE again.
328326

329327
m_bodyBuffer.insert(m_bodyBuffer.end(), m_buffer, m_buffer + m_bufferUsed);
330-
do {
331-
m_bufferUsed = 0;
328+
while (!m_readingData || m_bufferUsed != 0) {
332329
BOOL bResult = ::InternetReadFile(m_hWinInetRequest, m_buffer, sizeof(m_buffer), &m_bufferUsed);
330+
m_readingData = true;
333331
if (!bResult) {
334332
dwError = GetLastError();
335333
if (dwError == ERROR_IO_PENDING) {
@@ -339,18 +337,22 @@ class WinInetRequestWrapper
339337
// must stay valid and writable until the next
340338
// INTERNET_STATUS_REQUEST_COMPLETE callback comes
341339
// (that's why those are member variables).
340+
LOG_TRACE("InternetReadFile() failed: ERROR_IO_PENDING. Waiting for INTERNET_STATUS_REQUEST_COMPLETE to be called again");
342341
return;
343342
}
344343
LOG_WARN("InternetReadFile() failed: %d", dwError);
345344
break;
346345
}
347346

348347
m_bodyBuffer.insert(m_bodyBuffer.end(), m_buffer, m_buffer + m_bufferUsed);
349-
} while (m_bufferUsed == sizeof(m_buffer));
348+
}
350349
}
351350

351+
std::unique_ptr<SimpleHttpResponse> response(new SimpleHttpResponse(m_id));
352+
352353
// SUCCESS with no IO_PENDING means we're done with the response body: try to parse the response headers.
353354
if (dwError == ERROR_SUCCESS) {
355+
response->m_body = m_bodyBuffer;
354356
response->m_result = HttpResult_OK;
355357

356358
uint32_t value = 0;
@@ -564,4 +566,3 @@ bool HttpClient_WinInet::IsMsRootCheckRequired()
564566
#pragma warning(pop)
565567
#endif // HAVE_MAT_DEFAULT_HTTP_CLIENT
566568
// clang-format on
567-

0 commit comments

Comments
 (0)