mirror of https://github.com/aria2/aria2
Fixed assertion failure if Chunked encoding along with Content-Length is used.
parent
e73c3c53ff
commit
5bff877eae
|
@ -49,16 +49,28 @@ ssize_t SinkStreamFilter::transform
|
||||||
const SharedHandle<Segment>& segment,
|
const SharedHandle<Segment>& segment,
|
||||||
const unsigned char* inbuf, size_t inlen)
|
const unsigned char* inbuf, size_t inlen)
|
||||||
{
|
{
|
||||||
|
size_t wlen;
|
||||||
if(inlen > 0) {
|
if(inlen > 0) {
|
||||||
out->writeData(inbuf, inlen, segment->getPositionToWrite());
|
if(segment->getLength() > 0) {
|
||||||
|
// We must not write data larger than available space in
|
||||||
|
// segment.
|
||||||
|
assert(segment->getLength() >= segment->getWrittenLength());
|
||||||
|
size_t lenAvail = segment->getLength()-segment->getWrittenLength();
|
||||||
|
wlen = std::min(inlen, lenAvail);
|
||||||
|
} else {
|
||||||
|
wlen = inlen;
|
||||||
|
}
|
||||||
|
out->writeData(inbuf, wlen, segment->getPositionToWrite());
|
||||||
#ifdef ENABLE_MESSAGE_DIGEST
|
#ifdef ENABLE_MESSAGE_DIGEST
|
||||||
if(hashUpdate_) {
|
if(hashUpdate_) {
|
||||||
segment->updateHash(segment->getWrittenLength(), inbuf, inlen);
|
segment->updateHash(segment->getWrittenLength(), inbuf, wlen);
|
||||||
}
|
}
|
||||||
#endif // ENABLE_MESSAGE_DIGEST
|
#endif // ENABLE_MESSAGE_DIGEST
|
||||||
segment->updateWrittenLength(inlen);
|
segment->updateWrittenLength(wlen);
|
||||||
|
} else {
|
||||||
|
wlen = 0;
|
||||||
}
|
}
|
||||||
bytesProcessed_ = inlen;
|
bytesProcessed_ = wlen;
|
||||||
return bytesProcessed_;
|
return bytesProcessed_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -81,7 +81,8 @@ aria2c_SOURCES = AllTest.cc\
|
||||||
SegListTest.cc\
|
SegListTest.cc\
|
||||||
ParamedStringTest.cc\
|
ParamedStringTest.cc\
|
||||||
RpcHelperTest.cc\
|
RpcHelperTest.cc\
|
||||||
AbstractCommandTest.cc
|
AbstractCommandTest.cc\
|
||||||
|
SinkStreamFilterTest.cc
|
||||||
|
|
||||||
if ENABLE_XML_RPC
|
if ENABLE_XML_RPC
|
||||||
aria2c_SOURCES += XmlRpcRequestParserControllerTest.cc
|
aria2c_SOURCES += XmlRpcRequestParserControllerTest.cc
|
||||||
|
|
|
@ -0,0 +1,94 @@
|
||||||
|
#include "SinkStreamFilter.h"
|
||||||
|
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <iostream>
|
||||||
|
#include <cppunit/extensions/HelperMacros.h>
|
||||||
|
|
||||||
|
#include "Segment.h"
|
||||||
|
#include "ByteArrayDiskWriter.h"
|
||||||
|
#include "SinkStreamFilter.h"
|
||||||
|
#include "MockSegment.h"
|
||||||
|
|
||||||
|
namespace aria2 {
|
||||||
|
|
||||||
|
class SinkStreamFilterTest:public CppUnit::TestFixture {
|
||||||
|
|
||||||
|
CPPUNIT_TEST_SUITE(SinkStreamFilterTest);
|
||||||
|
CPPUNIT_TEST(testTransform_with_length);
|
||||||
|
CPPUNIT_TEST(testTransform_without_length);
|
||||||
|
CPPUNIT_TEST_SUITE_END();
|
||||||
|
|
||||||
|
class MockSegment2:public MockSegment {
|
||||||
|
public:
|
||||||
|
MockSegment2(int32_t length):length(length), writtenLength(0) {}
|
||||||
|
|
||||||
|
virtual int32_t getLength() const
|
||||||
|
{
|
||||||
|
return length;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual int32_t getWrittenLength() const
|
||||||
|
{
|
||||||
|
return writtenLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void updateWrittenLength(int32_t bytes)
|
||||||
|
{
|
||||||
|
writtenLength += bytes;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t length;
|
||||||
|
int32_t writtenLength;
|
||||||
|
};
|
||||||
|
|
||||||
|
SharedHandle<SinkStreamFilter> filter_;
|
||||||
|
SharedHandle<SinkStreamFilter> sinkFilter_;
|
||||||
|
SharedHandle<ByteArrayDiskWriter> writer_;
|
||||||
|
SharedHandle<MockSegment2> segment_;
|
||||||
|
|
||||||
|
void clearWriter()
|
||||||
|
{
|
||||||
|
writer_->setString("");
|
||||||
|
}
|
||||||
|
public:
|
||||||
|
void setUp()
|
||||||
|
{
|
||||||
|
writer_.reset(new ByteArrayDiskWriter());
|
||||||
|
sinkFilter_.reset(new SinkStreamFilter());
|
||||||
|
filter_.reset(new SinkStreamFilter(sinkFilter_));
|
||||||
|
sinkFilter_->init();
|
||||||
|
filter_->init();
|
||||||
|
segment_.reset(new MockSegment2(16));
|
||||||
|
}
|
||||||
|
|
||||||
|
void testTransform_with_length();
|
||||||
|
void testTransform_without_length();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
CPPUNIT_TEST_SUITE_REGISTRATION( SinkStreamFilterTest );
|
||||||
|
|
||||||
|
void SinkStreamFilterTest::testTransform_with_length()
|
||||||
|
{
|
||||||
|
// If segment_->getLength() > 0, make sure that at most
|
||||||
|
// segment_->getLength()-segment_->getWrittenLength() bytes are
|
||||||
|
// written.
|
||||||
|
std::string msg("01234567890123456");
|
||||||
|
ssize_t r = filter_->transform
|
||||||
|
(writer_, segment_,
|
||||||
|
reinterpret_cast<const unsigned char*>(msg.c_str()), msg.size());
|
||||||
|
CPPUNIT_ASSERT_EQUAL((ssize_t)16, r);
|
||||||
|
}
|
||||||
|
|
||||||
|
void SinkStreamFilterTest::testTransform_without_length()
|
||||||
|
{
|
||||||
|
// If segment_->getLength() == 0, all incoming bytes are written.
|
||||||
|
segment_->length = 0;
|
||||||
|
std::string msg("01234567890123456");
|
||||||
|
ssize_t r = filter_->transform
|
||||||
|
(writer_, segment_,
|
||||||
|
reinterpret_cast<const unsigned char*>(msg.c_str()), msg.size());
|
||||||
|
CPPUNIT_ASSERT_EQUAL((ssize_t)17, r);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace aria2
|
Loading…
Reference in New Issue