summaryrefslogtreecommitdiffstats
path: root/net/websockets
diff options
context:
space:
mode:
authortkent@chromium.org <tkent@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-09-20 05:37:56 +0000
committertkent@chromium.org <tkent@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-09-20 05:37:56 +0000
commitef530750f967bd5e606dae380d0c230bf586b522 (patch)
tree781f4cf8c230dc11fc050725d73a9451ca114a63 /net/websockets
parenta41b4e1e294a336a0e9589b432bb02d76121daca (diff)
downloadchromium_src-ef530750f967bd5e606dae380d0c230bf586b522.zip
chromium_src-ef530750f967bd5e606dae380d0c230bf586b522.tar.gz
chromium_src-ef530750f967bd5e606dae380d0c230bf586b522.tar.bz2
Revert 224271 "Introduce WebSocketInflater."
The new test WebSocketInflaterTest.LargeRandomDeflateInflate failed on XP Tests (dbg) and Win7 Tests (dbg). http://build.chromium.org/p/chromium.win/builders/Win7%20Tests%20%28dbg%29%282%29/builds/17568/steps/net_unittests/logs/stdio > [6994/6994] 376.29s WebSocketInflaterTest.LargeRandomDeflateInflate (0.73s) - retry #2 > Note: Google Test filter = WebSocketInflaterTest.LargeRandomDeflateInflate > [==========] Running 1 test from 1 test case. > [----------] Global test environment set-up. > [----------] 1 test from WebSocketInflaterTest > [ RUN ] WebSocketInflaterTest.LargeRandomDeflateInflate > c:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\include\vector(932) : Assertion failed: vector subscript out of range > c:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\include\vector(933) : Assertion failed: "Standard C++ Libraries Out of Range" && 0 > Introduce WebSocketInflater. > > Implement WebSocketInflater, a utility class for the permessage-deflate WebSocket extension. > > BUG=280910 > R=ricea, tyoshino > > Review URL: https://chromiumcodereview.appspot.com/23480049 TBR=yhirano@chromium.org Review URL: https://codereview.chromium.org/24078027 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@224292 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'net/websockets')
-rw-r--r--net/websockets/README3
-rw-r--r--net/websockets/websocket_inflater.cc280
-rw-r--r--net/websockets/websocket_inflater.h130
-rw-r--r--net/websockets/websocket_inflater_test.cc245
4 files changed, 0 insertions, 658 deletions
diff --git a/net/websockets/README b/net/websockets/README
index e9fd214f..1d1e1c3 100644
--- a/net/websockets/README
+++ b/net/websockets/README
@@ -53,9 +53,6 @@ websocket_frame_parser.cc
websocket_frame_parser.h
websocket_frame_parser_test.cc
websocket_frame_test.cc
-websocket_inflater.cc
-websocket_inflater.h
-websocket_inflater_test.cc
websocket_mux.h
websocket_stream_base.h
websocket_stream.cc
diff --git a/net/websockets/websocket_inflater.cc b/net/websockets/websocket_inflater.cc
deleted file mode 100644
index fbfb079..0000000
--- a/net/websockets/websocket_inflater.cc
+++ /dev/null
@@ -1,280 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "net/websockets/websocket_inflater.h"
-
-#include <algorithm>
-#include <deque>
-#include <vector>
-
-#include "base/logging.h"
-#include "net/base/io_buffer.h"
-#include "third_party/zlib/zlib.h"
-
-namespace net {
-
-namespace {
-
-class ShrinkableIOBufferWithSize : public IOBufferWithSize {
- public:
- explicit ShrinkableIOBufferWithSize(int size)
- : IOBufferWithSize(size) {}
-
- void Shrink(int new_size) {
- DCHECK_LE(new_size, size_);
- size_ = new_size;
- }
-
- private:
- virtual ~ShrinkableIOBufferWithSize() {}
-};
-
-} // namespace
-
-WebSocketInflater::WebSocketInflater()
- : input_queue_(kDefaultInputIOBufferCapacity),
- output_buffer_(kDefaultBufferCapacity) {}
-
-WebSocketInflater::WebSocketInflater(size_t input_queue_capacity,
- size_t output_buffer_capacity)
- : input_queue_(input_queue_capacity),
- output_buffer_(output_buffer_capacity) {
- DCHECK_GT(input_queue_capacity, 0u);
- DCHECK_GT(output_buffer_capacity, 0u);
-}
-
-bool WebSocketInflater::Initialize(int window_bits) {
- DCHECK_LE(8, window_bits);
- DCHECK_GE(15, window_bits);
- stream_.reset(new z_stream);
- memset(stream_.get(), 0, sizeof(*stream_));
- int result = inflateInit2(stream_.get(), -window_bits);
- if (result != Z_OK) {
- inflateEnd(stream_.get());
- stream_.reset();
- return false;
- }
- return true;
-}
-
-WebSocketInflater::~WebSocketInflater() {
- if (stream_) {
- inflateEnd(stream_.get());
- stream_.reset();
- }
-}
-
-bool WebSocketInflater::AddBytes(const char* data, size_t size) {
- if (!size)
- return true;
-
- if (!input_queue_.IsEmpty()) {
- // choked
- input_queue_.Push(data, size);
- return true;
- }
-
- int result = InflateWithFlush(data, size);
- if (stream_->avail_in > 0)
- input_queue_.Push(&data[size - stream_->avail_in], stream_->avail_in);
-
- return result == Z_OK || result == Z_BUF_ERROR;
-}
-
-bool WebSocketInflater::Finish() {
- return AddBytes("\x00\x00\xff\xff", 4);
-}
-
-scoped_refptr<IOBufferWithSize> WebSocketInflater::GetOutput(size_t size) {
- scoped_refptr<ShrinkableIOBufferWithSize> buffer =
- new ShrinkableIOBufferWithSize(size);
- size_t num_bytes_copied = 0;
-
- while (num_bytes_copied < size && output_buffer_.Size() > 0) {
- size_t num_bytes_to_copy =
- std::min(output_buffer_.Size(), size - num_bytes_copied);
- output_buffer_.Read(&buffer->data()[num_bytes_copied], num_bytes_to_copy);
- num_bytes_copied += num_bytes_to_copy;
- int result = InflateChokedInput();
- if (result != Z_OK && result != Z_BUF_ERROR)
- return NULL;
- }
- buffer->Shrink(num_bytes_copied);
- return buffer;
-}
-
-int WebSocketInflater::InflateWithFlush(const char* next_in, size_t avail_in) {
- int result = Inflate(next_in, avail_in, Z_NO_FLUSH);
- if (result != Z_OK && result != Z_BUF_ERROR)
- return result;
-
- if (CurrentOutputSize() > 0)
- return result;
- // CurrentOutputSize() == 0 means there is no data to be output,
- // so we should make sure it by using Z_SYNC_FLUSH.
- return Inflate(reinterpret_cast<const char*>(stream_->next_in),
- stream_->avail_in,
- Z_SYNC_FLUSH);
-}
-
-int WebSocketInflater::Inflate(const char* next_in,
- size_t avail_in,
- int flush) {
- stream_->next_in = reinterpret_cast<Bytef*>(const_cast<char*>(next_in));
- stream_->avail_in = avail_in;
-
- int result = Z_BUF_ERROR;
- do {
- std::pair<char*, size_t> tail = output_buffer_.GetTail();
- if (!tail.second)
- break;
-
- stream_->next_out = reinterpret_cast<Bytef*>(tail.first);
- stream_->avail_out = tail.second;
- result = inflate(stream_.get(), flush);
- output_buffer_.AdvanceTail(tail.second - stream_->avail_out);
- if (result == Z_STREAM_END) {
- // Received a block with BFINAL set to 1. Reset the decompression state.
- result = inflateReset(stream_.get());
- } else if (tail.second == stream_->avail_out) {
- break;
- }
- } while (result == Z_OK || result == Z_BUF_ERROR);
- return result;
-}
-
-int WebSocketInflater::InflateChokedInput() {
- if (input_queue_.IsEmpty())
- return InflateWithFlush(NULL, 0);
-
- int result = Z_BUF_ERROR;
- while (!input_queue_.IsEmpty()) {
- std::pair<char*, size_t> top = input_queue_.Top();
-
- result = InflateWithFlush(top.first, top.second);
- input_queue_.Consume(top.second - stream_->avail_in);
-
- if (result != Z_OK && result != Z_BUF_ERROR)
- return result;
-
- if (stream_->avail_in > 0) {
- // There are some data which are not consumed.
- break;
- }
- }
- return result;
-}
-
-WebSocketInflater::OutputBuffer::OutputBuffer(size_t capacity)
- : capacity_(capacity),
- buffer_(capacity_ + 1), // 1 for sentinel
- head_(0),
- tail_(0) {}
-
-WebSocketInflater::OutputBuffer::~OutputBuffer() {}
-
-size_t WebSocketInflater::OutputBuffer::Size() const {
- return (tail_ + buffer_.size() - head_) % buffer_.size();
-}
-
-std::pair<char*, size_t> WebSocketInflater::OutputBuffer::GetTail() {
- return std::make_pair(&buffer_[tail_],
- std::min(capacity_ - Size(), buffer_.size() - tail_));
-}
-
-void WebSocketInflater::OutputBuffer::Read(char* dest, size_t size) {
- DCHECK_LE(size, Size());
-
- size_t num_bytes_copied = 0;
- if (tail_ < head_) {
- size_t num_bytes_to_copy = std::min(size, buffer_.size() - head_);
- memcpy(&dest[num_bytes_copied], &buffer_[head_], num_bytes_to_copy);
- AdvanceHead(num_bytes_to_copy);
- num_bytes_copied += num_bytes_to_copy;
- }
-
- if (num_bytes_copied == size)
- return;
- DCHECK_LE(head_, tail_);
- size_t num_bytes_to_copy = size - num_bytes_copied;
- DCHECK_LE(num_bytes_to_copy, tail_ - head_);
- memcpy(&dest[num_bytes_copied], &buffer_[head_], num_bytes_to_copy);
- AdvanceHead(num_bytes_to_copy);
- num_bytes_copied += num_bytes_to_copy;
- DCHECK_EQ(size, num_bytes_copied);
- return;
-}
-
-void WebSocketInflater::OutputBuffer::AdvanceHead(size_t advance) {
- DCHECK_LE(advance, Size());
- head_ = (head_ + advance) % buffer_.size();
-}
-
-void WebSocketInflater::OutputBuffer::AdvanceTail(size_t advance) {
- DCHECK_LE(advance + Size(), capacity_);
- tail_ = (tail_ + advance) % buffer_.size();
-}
-
-WebSocketInflater::InputQueue::InputQueue(size_t capacity)
- : capacity_(capacity), head_of_first_buffer_(0), tail_of_last_buffer_(0) {}
-
-WebSocketInflater::InputQueue::~InputQueue() {}
-
-std::pair<char*, size_t> WebSocketInflater::InputQueue::Top() {
- DCHECK(!IsEmpty());
- if (buffers_.size() == 1) {
- return std::make_pair(&buffers_.front()->data()[head_of_first_buffer_],
- tail_of_last_buffer_ - head_of_first_buffer_);
- }
- return std::make_pair(&buffers_.front()->data()[head_of_first_buffer_],
- capacity_ - head_of_first_buffer_);
-}
-
-void WebSocketInflater::InputQueue::Push(const char* data, size_t size) {
- if (!size)
- return;
-
- size_t num_copied_bytes = 0;
- if (!IsEmpty())
- num_copied_bytes += PushToLastBuffer(data, size);
-
- while (num_copied_bytes < size) {
- DCHECK(IsEmpty() || tail_of_last_buffer_ == capacity_);
-
- buffers_.push_back(new IOBufferWithSize(capacity_));
- tail_of_last_buffer_ = 0;
- num_copied_bytes +=
- PushToLastBuffer(&data[num_copied_bytes], size - num_copied_bytes);
- }
-}
-
-void WebSocketInflater::InputQueue::Consume(size_t size) {
- DCHECK(!IsEmpty());
- DCHECK_LE(size + head_of_first_buffer_, capacity_);
-
- head_of_first_buffer_ += size;
- if (head_of_first_buffer_ == capacity_) {
- buffers_.pop_front();
- head_of_first_buffer_ = 0;
- }
- if (buffers_.size() == 1 && head_of_first_buffer_ == tail_of_last_buffer_) {
- buffers_.pop_front();
- head_of_first_buffer_ = 0;
- tail_of_last_buffer_ = 0;
- }
-}
-
-size_t WebSocketInflater::InputQueue::PushToLastBuffer(const char* data,
- size_t size) {
- DCHECK(!IsEmpty());
- size_t num_bytes_to_copy = std::min(size, capacity_ - tail_of_last_buffer_);
- if (!num_bytes_to_copy)
- return 0;
- IOBufferWithSize* buffer = buffers_.back().get();
- memcpy(&buffer->data()[tail_of_last_buffer_], data, num_bytes_to_copy);
- tail_of_last_buffer_ += num_bytes_to_copy;
- return num_bytes_to_copy;
-}
-
-} // namespace net
diff --git a/net/websockets/websocket_inflater.h b/net/websockets/websocket_inflater.h
deleted file mode 100644
index e57317f..0000000
--- a/net/websockets/websocket_inflater.h
+++ /dev/null
@@ -1,130 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef NET_WEBSOCKETS_WEBSOCKET_INFLATER_H_
-#define NET_WEBSOCKETS_WEBSOCKET_INFLATER_H_
-
-#include <deque>
-#include <utility>
-#include <vector>
-
-#include "base/basictypes.h"
-#include "base/memory/ref_counted.h"
-#include "base/memory/scoped_ptr.h"
-#include "net/base/net_export.h"
-
-extern "C" struct z_stream_s;
-
-namespace net {
-
-class IOBufferWithSize;
-
-// WebSocketInflater uncompresses data compressed by DEFLATE algorithm.
-class NET_EXPORT_PRIVATE WebSocketInflater {
- public:
- WebSocketInflater();
- // |input_queue_capacity| is a capacity for each contiguous block in the
- // input queue. The input queue can grow without limit.
- WebSocketInflater(size_t input_queue_capacity, size_t output_buffer_capacity);
- ~WebSocketInflater();
-
- // Returns true if there is no error.
- // |window_bits| must be between 8 and 15 (both inclusive).
- // This function must be called exactly once before calling any of the
- // following functions.
- bool Initialize(int window_bits);
-
- // Adds bytes to |stream_|.
- // Returns true if there is no error.
- // If the size of the output data reaches the capacity of the output buffer,
- // the following input data will be "choked", i.e. stored in the input queue,
- // staying compressed.
- bool AddBytes(const char* data, size_t size);
-
- // Flushes the input.
- // Returns true if there is no error.
- bool Finish();
-
- // Returns up to |size| bytes of the decompressed output.
- // Returns null if there is an inflation error.
- // The returned bytes will be dropped from the current output and never be
- // returned again.
- // If some input data is choked, calling this function may restart the
- // inflation process.
- // This means that even if you call |Finish()| and call |GetOutput()| with
- // size = |CurrentOutputSize()|, the inflater may have some remaining data.
- // To confirm the inflater emptiness, you should check whether
- // |CurrentOutputSize()| is zero.
- scoped_refptr<IOBufferWithSize> GetOutput(size_t size);
-
- // Returns the size of the current inflated output.
- size_t CurrentOutputSize() const { return output_buffer_.Size(); }
-
- static const size_t kDefaultBufferCapacity = 512;
- static const size_t kDefaultInputIOBufferCapacity = 512;
-
- private:
- // Ring buffer with fixed capacity.
- class OutputBuffer {
- public:
- explicit OutputBuffer(size_t capacity);
- ~OutputBuffer();
-
- size_t Size() const;
- // Returns (tail pointer, availabe size).
- // A user can push data to the queue by writing the data to
- // the area returned by this function and calling AdvanceTail.
- std::pair<char*, size_t> GetTail();
- void Read(char* dest, size_t size);
- void AdvanceTail(size_t advance);
-
- private:
- void AdvanceHead(size_t advance);
-
- const size_t capacity_;
- std::vector<char> buffer_;
- size_t head_;
- size_t tail_;
- };
-
- class InputQueue {
- public:
- // |capacity| is used for the capacity of each IOBuffer in this queue.
- // this queue itself can grow without limit.
- explicit InputQueue(size_t capacity);
- ~InputQueue();
-
- // Returns (data pointer, size), the first component of unconsumed data.
- // The type of data pointer is non-const because |inflate| function
- // requires so.
- std::pair<char*, size_t> Top();
- bool IsEmpty() const { return buffers_.empty(); }
- void Push(const char* data, size_t size);
- // Consumes the topmost |size| bytes.
- // |size| must be less than or equal to the first buffer size.
- void Consume(size_t size);
-
- private:
- size_t PushToLastBuffer(const char* data, size_t size);
-
- const size_t capacity_;
- size_t head_of_first_buffer_;
- size_t tail_of_last_buffer_;
- std::deque<scoped_refptr<IOBufferWithSize> > buffers_;
- };
-
- int InflateWithFlush(const char* next_in, size_t avail_in);
- int Inflate(const char* next_in, size_t avail_in, int flush);
- int InflateChokedInput();
-
- scoped_ptr<z_stream_s> stream_;
- InputQueue input_queue_;
- OutputBuffer output_buffer_;
-
- DISALLOW_COPY_AND_ASSIGN(WebSocketInflater);
-};
-
-} // namespace net
-
-#endif // NET_WEBSOCKETS_WEBSOCKET_INFLATER_H_
diff --git a/net/websockets/websocket_inflater_test.cc b/net/websockets/websocket_inflater_test.cc
deleted file mode 100644
index 722e29e8..0000000
--- a/net/websockets/websocket_inflater_test.cc
+++ /dev/null
@@ -1,245 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "net/websockets/websocket_inflater.h"
-
-#include <stdint.h>
-#include <string>
-#include <vector>
-
-#include "base/memory/ref_counted.h"
-#include "net/base/io_buffer.h"
-#include "net/websockets/websocket_deflater.h"
-#include "testing/gtest/include/gtest/gtest.h"
-
-namespace net {
-
-namespace {
-
-std::string ToString(IOBufferWithSize* buffer) {
- return std::string(buffer->data(), buffer->size());
-}
-
-class LinearCongruentialGenerator {
- public:
- explicit LinearCongruentialGenerator(uint32_t seed);
- uint32_t Generate();
-
- private:
- uint32_t current_;
-
- static const uint32_t a_ = 1103515245;
- static const uint32_t c_ = 12345;
- static const uint32_t m_ = 1 << 31;
-};
-
-LinearCongruentialGenerator::LinearCongruentialGenerator(uint32_t seed)
- : current_(seed) {}
-
-uint32_t LinearCongruentialGenerator::Generate() {
- uint32_t result = current_;
- current_ = (current_ * a_ + c_) % m_;
- return result;
-}
-
-TEST(WebSocketInflaterTest, Construct) {
- WebSocketInflater inflater;
- ASSERT_TRUE(inflater.Initialize(15));
-
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-}
-
-TEST(WebSocketInflaterTest, InflateHelloTakeOverContext) {
- WebSocketInflater inflater;
- ASSERT_TRUE(inflater.Initialize(15));
- scoped_refptr<IOBufferWithSize> actual1, actual2;
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- actual1 = inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(actual1);
- EXPECT_EQ("Hello", ToString(actual1.get()));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x00\x11\x00\x00", 5));
- ASSERT_TRUE(inflater.Finish());
- actual2 = inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(actual2);
- EXPECT_EQ("Hello", ToString(actual2.get()));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-}
-
-TEST(WebSocketInflaterTest, InflateHelloSmallCapacity) {
- WebSocketInflater inflater(1, 1);
- ASSERT_TRUE(inflater.Initialize(15));
- std::string actual;
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- for (size_t i = 0; i < 5; ++i) {
- ASSERT_EQ(1u, inflater.CurrentOutputSize());
- scoped_refptr<IOBufferWithSize> buffer = inflater.GetOutput(1);
- ASSERT_TRUE(buffer);
- ASSERT_EQ(1, buffer->size());
- actual += ToString(buffer.get());
- }
- EXPECT_EQ("Hello", actual);
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-}
-
-TEST(WebSocketInflaterTest, InflateHelloSmallCapacityGetTotalOutput) {
- WebSocketInflater inflater(1, 1);
- ASSERT_TRUE(inflater.Initialize(15));
- scoped_refptr<IOBufferWithSize> actual;
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- ASSERT_EQ(1u, inflater.CurrentOutputSize());
- actual = inflater.GetOutput(1024);
- EXPECT_EQ("Hello", ToString(actual));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-}
-
-TEST(WebSocketInflaterTest, InflateInvalidData) {
- WebSocketInflater inflater;
- ASSERT_TRUE(inflater.Initialize(15));
- EXPECT_FALSE(inflater.AddBytes("\xf2\x48\xcd\xc9INVALID DATA", 16));
-}
-
-TEST(WebSocketInflaterTest, ChokedInvalidData) {
- WebSocketInflater inflater(1, 1);
- ASSERT_TRUE(inflater.Initialize(15));
-
- EXPECT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9INVALID DATA", 16));
- EXPECT_TRUE(inflater.Finish());
- EXPECT_EQ(1u, inflater.CurrentOutputSize());
- EXPECT_FALSE(inflater.GetOutput(1024));
-}
-
-TEST(WebSocketInflaterTest, MultipleAddBytesCalls) {
- WebSocketInflater inflater;
- ASSERT_TRUE(inflater.Initialize(15));
- std::string input("\xf2\x48\xcd\xc9\xc9\x07\x00", 7);
- scoped_refptr<IOBufferWithSize> actual;
-
- for (size_t i = 0; i < input.size(); ++i) {
- ASSERT_TRUE(inflater.AddBytes(&input[i], 1));
- }
- ASSERT_TRUE(inflater.Finish());
- actual = inflater.GetOutput(5);
- ASSERT_TRUE(actual);
- EXPECT_EQ("Hello", ToString(actual.get()));
-}
-
-TEST(WebSocketInflaterTest, Reset) {
- WebSocketInflater inflater;
- ASSERT_TRUE(inflater.Initialize(15));
- scoped_refptr<IOBufferWithSize> actual1, actual2;
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- actual1 = inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(actual1);
- EXPECT_EQ("Hello", ToString(actual1.get()));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-
- // Reset the stream with a block [BFINAL = 1, BTYPE = 00, LEN = 0]
- ASSERT_TRUE(inflater.AddBytes("\x01", 1));
- ASSERT_TRUE(inflater.Finish());
- ASSERT_EQ(0u, inflater.CurrentOutputSize());
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- actual2 = inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(actual2);
- EXPECT_EQ("Hello", ToString(actual2.get()));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-}
-
-TEST(WebSocketInflaterTest, ResetAndLostContext) {
- WebSocketInflater inflater;
- scoped_refptr<IOBufferWithSize> actual1, actual2;
- ASSERT_TRUE(inflater.Initialize(15));
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- actual1 = inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(actual1);
- EXPECT_EQ("Hello", ToString(actual1.get()));
- EXPECT_EQ(0u, inflater.CurrentOutputSize());
-
- // Reset the stream with a block [BFINAL = 1, BTYPE = 00, LEN = 0]
- ASSERT_TRUE(inflater.AddBytes("\x01", 1));
- ASSERT_TRUE(inflater.Finish());
- ASSERT_EQ(0u, inflater.CurrentOutputSize());
-
- // The context is already reset.
- ASSERT_FALSE(inflater.AddBytes("\xf2\x00\x11\x00\x00", 5));
-}
-
-TEST(WebSocketInflaterTest, CallAddBytesAndFinishWithoutGetOutput) {
- WebSocketInflater inflater;
- scoped_refptr<IOBufferWithSize> actual1, actual2;
- ASSERT_TRUE(inflater.Initialize(15));
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- EXPECT_EQ(5u, inflater.CurrentOutputSize());
-
- // This is a test for detecting memory leaks with valgrind.
-}
-
-TEST(WebSocketInflaterTest, CallAddBytesAndFinishWithoutGetOutputChoked) {
- WebSocketInflater inflater(1, 1);
- scoped_refptr<IOBufferWithSize> actual1, actual2;
- ASSERT_TRUE(inflater.Initialize(15));
-
- ASSERT_TRUE(inflater.AddBytes("\xf2\x48\xcd\xc9\xc9\x07\x00", 7));
- ASSERT_TRUE(inflater.Finish());
- EXPECT_EQ(1u, inflater.CurrentOutputSize());
-
- // This is a test for detecting memory leaks with valgrind.
-}
-
-TEST(WebSocketInflaterTest, LargeRandomDeflateInflate) {
- const size_t size = 64 * 1024;
- LinearCongruentialGenerator generator(133);
- std::vector<char> input;
- std::vector<char> output;
- scoped_refptr<IOBufferWithSize> compressed;
-
- WebSocketDeflater deflater(WebSocketDeflater::TAKE_OVER_CONTEXT);
- ASSERT_TRUE(deflater.Initialize(8));
- WebSocketInflater inflater(256, 256);
- ASSERT_TRUE(inflater.Initialize(8));
-
- for (size_t i = 0; i < size; ++i)
- input.push_back(static_cast<char>(generator.Generate()));
-
- ASSERT_TRUE(deflater.AddBytes(&input[0], input.size()));
- ASSERT_TRUE(deflater.Finish());
-
- compressed = deflater.GetOutput(deflater.CurrentOutputSize());
-
- ASSERT_TRUE(compressed);
- ASSERT_EQ(0u, deflater.CurrentOutputSize());
-
- ASSERT_TRUE(inflater.AddBytes(compressed->data(), compressed->size()));
- ASSERT_TRUE(inflater.Finish());
-
- while (inflater.CurrentOutputSize() > 0) {
- scoped_refptr<IOBufferWithSize> uncompressed =
- inflater.GetOutput(inflater.CurrentOutputSize());
- ASSERT_TRUE(uncompressed);
- output.insert(output.end(),
- uncompressed->data(),
- uncompressed->data() + uncompressed->size());
- }
-
- EXPECT_EQ(output, input);
-}
-
-} // unnamed namespace
-
-} // namespace net