Merge pull request #5760 from Icinga/fix/http-client-bugs

Fix incorrect socket handling for the HTTP client
This commit is contained in:
Michael Friedrich 2017-12-08 12:51:50 +01:00 committed by GitHub
commit a72a7b7c89
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 27 additions and 15 deletions

View File

@ -145,6 +145,9 @@ bool StreamReadContext::FillFromStream(const Stream::Ptr& stream, bool may_wait)
if (!Buffer)
throw std::bad_alloc();
if (stream->IsEof())
break;
size_t rc = stream->Read(Buffer + Size, 4096, true);
Size += rc;

View File

@ -158,12 +158,7 @@ bool HttpResponse::Parse(StreamReadContext& src, bool may_wait)
if (line == "") {
m_State = HttpResponseBody;
/* we're done if the request doesn't contain a message body */
if (!Headers->Contains("content-length") && !Headers->Contains("transfer-encoding"))
Complete = true;
else
m_Body = new FIFO();
m_Body = new FIFO();
return true;
@ -203,27 +198,41 @@ bool HttpResponse::Parse(StreamReadContext& src, bool may_wait)
return true;
}
} else {
if (src.Eof)
bool hasLengthIndicator = false;
size_t lengthIndicator = 0;
Value contentLengthHeader;
if (Headers->Get("content-length", &contentLengthHeader)) {
hasLengthIndicator = true;
lengthIndicator = Convert::ToLong(contentLengthHeader);
}
if (hasLengthIndicator && src.Eof)
BOOST_THROW_EXCEPTION(std::invalid_argument("Unexpected EOF in HTTP body"));
if (src.MustRead) {
if (!src.FillFromStream(m_Stream, false)) {
if (!src.FillFromStream(m_Stream, may_wait))
src.Eof = true;
BOOST_THROW_EXCEPTION(std::invalid_argument("Unexpected EOF in HTTP body"));
}
src.MustRead = false;
}
size_t length_indicator = Convert::ToLong(Headers->Get("content-length"));
if (!hasLengthIndicator)
lengthIndicator = src.Size;
if (src.Size < length_indicator) {
if (src.Size < lengthIndicator) {
src.MustRead = true;
return false;
return may_wait;
}
m_Body->Write(src.Buffer, lengthIndicator);
src.DropData(lengthIndicator);
if (!hasLengthIndicator && !src.Eof) {
src.MustRead = true;
return may_wait;
}
m_Body->Write(src.Buffer, length_indicator);
src.DropData(length_indicator);
Complete = true;
return true;
}