@@ -224,7 +224,7 @@ class winhttp_request_context : public request_context
224
224
225
225
size64_t m_remaining_to_write;
226
226
227
- std::char_traits<uint8_t >::pos_type m_readbuf_pos ;
227
+ std::char_traits<uint8_t >::pos_type m_startingPosition ;
228
228
229
229
// If the user specified that to guarantee data buffering of request data, in case of challenged authentication requests, etc...
230
230
// Then if the request stream buffer doesn't support seeking we need to copy the body chunks as it is sent.
@@ -262,7 +262,7 @@ class winhttp_request_context : public request_context
262
262
: request_context(client, request),
263
263
m_request_handle (nullptr ),
264
264
m_bodyType(no_body),
265
- m_readbuf_pos( 0 ),
265
+ m_startingPosition(std::char_traits< uint8_t >::eof() ),
266
266
m_body_data(),
267
267
m_remaining_to_write(0 ),
268
268
m_proxy_authentication_tried(false ),
@@ -674,7 +674,9 @@ class winhttp_client : public _http_client_communicator
674
674
return ;
675
675
}
676
676
677
- winhttp_context->m_readbuf_pos = rbuf.getpos (std::ios_base::in);
677
+ // Record starting position incase request is challenged for authorization
678
+ // and needs to seek back to where reading is started from.
679
+ winhttp_context->m_startingPosition = rbuf.getpos (std::ios_base::in);
678
680
679
681
// If we find ourselves here, we either don't know how large the message
680
682
// body is, or it is larger than our threshold.
@@ -717,6 +719,8 @@ class winhttp_client : public _http_client_communicator
717
719
// If the read buffer for copying exists then write to it.
718
720
if (p_request_context->m_readBufferCopy )
719
721
{
722
+ // We have raw memory here writing to a memory stream so it is safe to wait
723
+ // since it will always be non-blocking.
720
724
p_request_context->m_readBufferCopy ->putn (&p_request_context->m_body_data .get ()[http::details::chunked_encoding::data_offset], bytes_read).wait ();
721
725
}
722
726
}
@@ -736,7 +740,7 @@ class winhttp_client : public _http_client_communicator
736
740
p_request_context->m_bodyType = no_body;
737
741
if (p_request_context->m_readBufferCopy )
738
742
{
739
- // Move the saved buffer into the read buffer.
743
+ // Move the saved buffer into the read buffer, which now supports seeking .
740
744
p_request_context->m_readStream = concurrency::streams::container_stream<std::vector<uint8_t >>::open_istream (std::move (p_request_context->m_readBufferCopy ->collection ()));
741
745
p_request_context->m_readBufferCopy .reset ();
742
746
}
@@ -864,10 +868,6 @@ class winhttp_client : public _http_client_communicator
864
868
_ASSERTE (response.status_code () == status_codes::Unauthorized || response.status_code () == status_codes::ProxyAuthRequired
865
869
|| error == ERROR_WINHTTP_RESEND_REQUEST);
866
870
867
- // If the application set a stream for the request body, we can only resend if the input stream supports
868
- // seeking and we are also successful in seeking to the position we started at when the original request
869
- // was sent.
870
-
871
871
bool got_credentials = false ;
872
872
BOOL results;
873
873
DWORD dwSupportedSchemes;
@@ -877,22 +877,16 @@ class winhttp_client : public _http_client_communicator
877
877
string_t username;
878
878
string_t password;
879
879
880
- if (request.body ())
880
+ // Check if the saved read position is valid
881
+ auto rdpos = p_request_context->m_startingPosition ;
882
+ if (rdpos != static_cast <std::char_traits<uint8_t >::pos_type>(std::char_traits<uint8_t >::eof ()))
881
883
{
882
- // Valid request stream => msg has a body that needs to be resend
883
-
884
- auto rdpos = p_request_context->m_readbuf_pos ;
884
+ auto rbuf = p_request_context->_get_readbuffer ();
885
885
886
- // Check if the saved read position is valid
887
- if (rdpos != ( std::char_traits< uint8_t >::pos_type) - 1 )
886
+ // Try to seek back to the saved read position
887
+ if (rbuf. seekpos ( rdpos, std::ios::ios_base::in) != rdpos )
888
888
{
889
- auto rbuf = p_request_context->_get_readbuffer ();
890
-
891
- if (rbuf.is_open ())
892
- {
893
- // Try to seek back to the saved read position
894
- rbuf.seekpos (rdpos, std::ios::ios_base::in);
895
- }
889
+ return false ;
896
890
}
897
891
}
898
892
0 commit comments