Work around libevent bug 306 in evbuffer_add_file.
See <https://github.com/libevent/libevent/issues/306> for details.
This commit is contained in:
parent
bb7fb95b57
commit
eed2a69f7a
|
@ -76,12 +76,25 @@ TEST(EvBufferTest, AddFileTest) {
|
|||
// Ensure adding the whole file succeeds.
|
||||
EvBuffer buf1;
|
||||
ASSERT_TRUE(buf1.AddFile(in_fd, 0, 3, &error_message)) << error_message;
|
||||
in_fd = -1;
|
||||
EXPECT_EQ(3u, evbuffer_get_length(buf1.get()));
|
||||
|
||||
// Ensure adding an empty region succeeds.
|
||||
EvBuffer buf2;
|
||||
ASSERT_TRUE(buf2.AddFile(in_fd, 0, 0, &error_message)) << error_message;
|
||||
EXPECT_EQ(0u, evbuffer_get_length(buf2.get()));
|
||||
|
||||
// Ensure adding part of a file after another string succeeds.
|
||||
in_fd = open(foo_filename.c_str(), O_RDONLY);
|
||||
EvBuffer buf3;
|
||||
buf3.Add("1234");
|
||||
ASSERT_TRUE(buf3.AddFile(in_fd, 1, 2, &error_message)) << error_message;
|
||||
auto size3 = evbuffer_get_length(buf3.get());
|
||||
EXPECT_EQ(6u, size3);
|
||||
std::string buf3_contents = std::string(
|
||||
reinterpret_cast<const char *>(evbuffer_pullup(buf3.get(), size3)),
|
||||
size3);
|
||||
EXPECT_EQ("1234oo", buf3_contents);
|
||||
}
|
||||
|
||||
class FileSlicesTest : public testing::Test {
|
||||
|
|
17
src/http.cc
17
src/http.cc
|
@ -176,6 +176,23 @@ bool EvBuffer::AddFile(int fd, ev_off_t offset, ev_off_t length,
|
|||
return true;
|
||||
}
|
||||
|
||||
if (evbuffer_get_length(buf_) > 0) {
|
||||
// Work around https://github.com/libevent/libevent/issues/306 by using a
|
||||
// fresh buffer for evbuffer_add_file.
|
||||
EvBuffer fresh_buffer;
|
||||
if (!fresh_buffer.AddFile(fd, offset, length, error_message)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Crash if evbuffer_add_buffer fails, because the ownership of |fd| has
|
||||
// already been transferred, and it's too confusing to support some
|
||||
// failures in which the caller still owns |fd| and some in which it does
|
||||
// not.
|
||||
CHECK_EQ(0, evbuffer_add_buffer(buf_, fresh_buffer.buf_))
|
||||
<< "evbuffer_add_buffer failed: " << strerror(errno);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (evbuffer_add_file(buf_, fd, offset, length) != 0) {
|
||||
int err = errno;
|
||||
*error_message = StrCat("evbuffer_add_file failed with offset ", offset,
|
||||
|
|
Loading…
Reference in New Issue