// Copyright 2015 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 <stddef.h>
#include <stdint.h>
#include <string.h>
#include <utility>

#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/callback.h"
#include "base/files/file_path.h"
#include "base/location.h"
#include "base/macros.h"
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_loop.h"
#include "base/run_loop.h"
#include "base/strings/stringprintf.h"
#include "base/task_runner.h"
#include "base/time/time.h"
#include "content/public/test/async_file_test_helper.h"
#include "content/public/test/test_file_system_context.h"
#include "net/base/completion_callback.h"
#include "net/base/io_buffer.h"
#include "net/base/net_errors.h"
#include "net/base/test_completion_callback.h"
#include "net/disk_cache/disk_cache.h"
#include "storage/browser/blob/blob_data_builder.h"
#include "storage/browser/blob/blob_data_handle.h"
#include "storage/browser/blob/blob_reader.h"
#include "storage/browser/blob/blob_storage_context.h"
#include "storage/browser/fileapi/file_stream_reader.h"
#include "storage/browser/fileapi/file_system_context.h"
#include "storage/browser/fileapi/file_system_file_util.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "url/gurl.h"

using base::FilePath;
using content::AsyncFileTestHelper;
using net::DrainableIOBuffer;
using net::IOBuffer;

namespace storage {
namespace {

const int kTestDiskCacheStreamIndex = 0;

// Our disk cache tests don't need a real data handle since the tests themselves
// scope the disk cache and entries.
class EmptyDataHandle : public storage::BlobDataBuilder::DataHandle {
 private:
  ~EmptyDataHandle() override {}
};

// A disk_cache::Entry that arbitrarily delays the completion of a read
// operation to allow testing some races without flake. This is particularly
// relevant in this unit test, which uses the always-synchronous MEMORY_CACHE.
class DelayedReadEntry : public disk_cache::Entry {
 public:
  explicit DelayedReadEntry(disk_cache::ScopedEntryPtr entry)
      : entry_(std::move(entry)) {}
  ~DelayedReadEntry() override { EXPECT_FALSE(HasPendingReadCallbacks()); }

  bool HasPendingReadCallbacks() { return !pending_read_callbacks_.empty(); }

  void RunPendingReadCallbacks() {
    std::vector<base::Callback<void(void)>> callbacks;
    pending_read_callbacks_.swap(callbacks);
    for (const auto& callback : callbacks)
      callback.Run();
  }

  // From disk_cache::Entry:
  void Doom() override { entry_->Doom(); }

  void Close() override { delete this; }  // Note this is required by the API.

  std::string GetKey() const override { return entry_->GetKey(); }

  base::Time GetLastUsed() const override { return entry_->GetLastUsed(); }

  base::Time GetLastModified() const override {
    return entry_->GetLastModified();
  }

  int32_t GetDataSize(int index) const override {
    return entry_->GetDataSize(index);
  }

  int ReadData(int index,
               int offset,
               IOBuffer* buf,
               int buf_len,
               const CompletionCallback& original_callback) override {
    net::TestCompletionCallback callback;
    int rv = entry_->ReadData(index, offset, buf, buf_len, callback.callback());
    DCHECK_NE(rv, net::ERR_IO_PENDING)
        << "Test expects to use a MEMORY_CACHE instance, which is synchronous.";
    pending_read_callbacks_.push_back(base::Bind(original_callback, rv));
    return net::ERR_IO_PENDING;
  }

  int WriteData(int index,
                int offset,
                IOBuffer* buf,
                int buf_len,
                const CompletionCallback& callback,
                bool truncate) override {
    return entry_->WriteData(index, offset, buf, buf_len, callback, truncate);
  }

  int ReadSparseData(int64_t offset,
                     IOBuffer* buf,
                     int buf_len,
                     const CompletionCallback& callback) override {
    return entry_->ReadSparseData(offset, buf, buf_len, callback);
  }

  int WriteSparseData(int64_t offset,
                      IOBuffer* buf,
                      int buf_len,
                      const CompletionCallback& callback) override {
    return entry_->WriteSparseData(offset, buf, buf_len, callback);
  }

  int GetAvailableRange(int64_t offset,
                        int len,
                        int64_t* start,
                        const CompletionCallback& callback) override {
    return entry_->GetAvailableRange(offset, len, start, callback);
  }

  bool CouldBeSparse() const override { return entry_->CouldBeSparse(); }

  void CancelSparseIO() override { entry_->CancelSparseIO(); }

  int ReadyForSparseIO(const CompletionCallback& callback) override {
    return entry_->ReadyForSparseIO(callback);
  }

 private:
  disk_cache::ScopedEntryPtr entry_;
  std::vector<base::Callback<void(void)>> pending_read_callbacks_;
};

scoped_ptr<disk_cache::Backend> CreateInMemoryDiskCache(
    const scoped_refptr<base::SingleThreadTaskRunner>& thread) {
  scoped_ptr<disk_cache::Backend> cache;
  net::TestCompletionCallback callback;
  int rv = disk_cache::CreateCacheBackend(
      net::MEMORY_CACHE, net::CACHE_BACKEND_DEFAULT, FilePath(), 0, false,
      thread, nullptr, &cache, callback.callback());
  EXPECT_EQ(net::OK, callback.GetResult(rv));

  return cache;
}

disk_cache::ScopedEntryPtr CreateDiskCacheEntry(disk_cache::Backend* cache,
                                                const char* key,
                                                const std::string& data) {
  disk_cache::Entry* temp_entry = nullptr;
  net::TestCompletionCallback callback;
  int rv = cache->CreateEntry(key, &temp_entry, callback.callback());
  if (callback.GetResult(rv) != net::OK)
    return nullptr;
  disk_cache::ScopedEntryPtr entry(temp_entry);

  scoped_refptr<net::StringIOBuffer> iobuffer = new net::StringIOBuffer(data);
  rv = entry->WriteData(kTestDiskCacheStreamIndex, 0, iobuffer.get(),
                        iobuffer->size(), callback.callback(), false);
  EXPECT_EQ(static_cast<int>(data.size()), callback.GetResult(rv));
  return entry;
}

template <typename T>
void SetValue(T* address, T value) {
  *address = value;
}

class FakeFileStreamReader : public FileStreamReader {
 public:
  explicit FakeFileStreamReader(const std::string& contents)
      : buffer_(new DrainableIOBuffer(
            new net::StringIOBuffer(
                scoped_ptr<std::string>(new std::string(contents))),
            contents.size())),
        net_error_(net::OK),
        size_(contents.size()) {}
  FakeFileStreamReader(const std::string& contents, uint64_t size)
      : buffer_(new DrainableIOBuffer(
            new net::StringIOBuffer(
                scoped_ptr<std::string>(new std::string(contents))),
            contents.size())),
        net_error_(net::OK),
        size_(size) {}

  ~FakeFileStreamReader() override {}

  void SetReturnError(int net_error) { net_error_ = net_error; }

  void SetAsyncRunner(base::SingleThreadTaskRunner* runner) {
    async_task_runner_ = runner;
  }

  int Read(net::IOBuffer* buf,
           int buf_length,
           const net::CompletionCallback& done) override {
    DCHECK(buf);
    // When async_task_runner_ is not set, return synchronously.
    if (!async_task_runner_.get()) {
      if (net_error_ == net::OK) {
        return ReadImpl(buf, buf_length, net::CompletionCallback());
      } else {
        return net_error_;
      }
    }

    // Otherwise always return asynchronously.
    if (net_error_ == net::OK) {
      async_task_runner_->PostTask(
          FROM_HERE,
          base::Bind(base::IgnoreResult(&FakeFileStreamReader::ReadImpl),
                     base::Unretained(this), make_scoped_refptr(buf),
                     buf_length, done));
    } else {
      async_task_runner_->PostTask(FROM_HERE, base::Bind(done, net_error_));
    }
    return net::ERR_IO_PENDING;
  }

  int64_t GetLength(
      const net::Int64CompletionCallback& size_callback) override {
    // When async_task_runner_ is not set, return synchronously.
    if (!async_task_runner_.get()) {
      if (net_error_ == net::OK) {
        return size_;
      } else {
        return net_error_;
      }
    }
    if (net_error_ == net::OK) {
      async_task_runner_->PostTask(FROM_HERE, base::Bind(size_callback, size_));
    } else {
      async_task_runner_->PostTask(
          FROM_HERE,
          base::Bind(size_callback, static_cast<int64_t>(net_error_)));
    }
    return net::ERR_IO_PENDING;
  }

 private:
  int ReadImpl(scoped_refptr<net::IOBuffer> buf,
               int buf_length,
               const net::CompletionCallback& done) {
    CHECK_GE(buf_length, 0);
    int length = std::min(buf_length, buffer_->BytesRemaining());
    memcpy(buf->data(), buffer_->data(), length);
    buffer_->DidConsume(length);
    if (done.is_null()) {
      return length;
    }
    done.Run(length);
    return net::ERR_IO_PENDING;
  }

  scoped_refptr<net::DrainableIOBuffer> buffer_;
  scoped_refptr<base::SingleThreadTaskRunner> async_task_runner_;
  int net_error_;
  uint64_t size_;

  DISALLOW_COPY_AND_ASSIGN(FakeFileStreamReader);
};

class MockFileStreamReaderProvider
    : public BlobReader::FileStreamReaderProvider {
 public:
  ~MockFileStreamReaderProvider() override {}

  MOCK_METHOD4(CreateForLocalFileMock,
               FileStreamReader*(base::TaskRunner* task_runner,
                                 const FilePath& file_path,
                                 int64_t initial_offset,
                                 const base::Time& expected_modification_time));
  MOCK_METHOD4(CreateFileStreamReaderMock,
               FileStreamReader*(const GURL& filesystem_url,
                                 int64_t offset,
                                 int64_t max_bytes_to_read,
                                 const base::Time& expected_modification_time));
  // Since we're returning a move-only type, we have to do some delegation for
  // gmock.
  scoped_ptr<FileStreamReader> CreateForLocalFile(
      base::TaskRunner* task_runner,
      const base::FilePath& file_path,
      int64_t initial_offset,
      const base::Time& expected_modification_time) override {
    return make_scoped_ptr(CreateForLocalFileMock(
        task_runner, file_path, initial_offset, expected_modification_time));
  }

  scoped_ptr<FileStreamReader> CreateFileStreamReader(
      const GURL& filesystem_url,
      int64_t offset,
      int64_t max_bytes_to_read,
      const base::Time& expected_modification_time) override {
    return make_scoped_ptr(CreateFileStreamReaderMock(
        filesystem_url, offset, max_bytes_to_read, expected_modification_time));
  }
};

}  // namespace

class BlobReaderTest : public ::testing::Test {
 public:
  BlobReaderTest() {}
  ~BlobReaderTest() override {}

  void TearDown() override {
    reader_.reset();
    blob_handle_.reset();
    message_loop_.RunUntilIdle();
    base::RunLoop().RunUntilIdle();
  }

 protected:
  void InitializeReader(BlobDataBuilder* builder) {
    blob_handle_ = builder ? context_.AddFinishedBlob(builder) : nullptr;
    provider_ = new MockFileStreamReaderProvider();
    scoped_ptr<BlobReader::FileStreamReaderProvider> temp_ptr(provider_);
    reader_.reset(new BlobReader(blob_handle_.get(), std::move(temp_ptr),
                                 message_loop_.task_runner().get()));
  }

  // Takes ownership of the file reader (the blob reader takes ownership).
  void ExpectLocalFileCall(const FilePath& file_path,
                           base::Time modification_time,
                           uint64_t initial_offset,
                           FakeFileStreamReader* reader) {
    EXPECT_CALL(*provider_, CreateForLocalFileMock(
                                message_loop_.task_runner().get(), file_path,
                                initial_offset, modification_time))
        .WillOnce(testing::Return(reader));
  }

  // Takes ownership of the file reader (the blob reader takes ownership).
  void ExpectFileSystemCall(const GURL& filesystem_url,
                            int64_t offset,
                            int64_t max_bytes_to_read,
                            base::Time expected_modification_time,
                            FakeFileStreamReader* reader) {
    EXPECT_CALL(*provider_, CreateFileStreamReaderMock(
                                filesystem_url, offset, max_bytes_to_read,
                                expected_modification_time))
        .WillOnce(testing::Return(reader));
  }

  void CheckSizeCalculatedSynchronously(size_t expected_size, int async_size) {
    EXPECT_EQ(-1, async_size);
    EXPECT_EQ(net::OK, reader_->net_error());
    EXPECT_EQ(expected_size, reader_->total_size());
    EXPECT_TRUE(reader_->total_size_calculated());
  }

  void CheckSizeNotCalculatedYet(int async_size) {
    EXPECT_EQ(-1, async_size);
    EXPECT_EQ(net::OK, reader_->net_error());
    EXPECT_FALSE(reader_->total_size_calculated());
  }

  void CheckSizeCalculatedAsynchronously(size_t expected_size,
                                         int async_result) {
    EXPECT_EQ(net::OK, async_result);
    EXPECT_EQ(net::OK, reader_->net_error());
    EXPECT_EQ(expected_size, reader_->total_size());
    EXPECT_TRUE(reader_->total_size_calculated());
  }

  scoped_refptr<net::IOBuffer> CreateBuffer(uint64_t size) {
    return scoped_refptr<net::IOBuffer>(
        new net::IOBuffer(static_cast<size_t>(size)));
  }

  bool IsReaderTotalSizeCalculated() {
    return reader_->total_size_calculated();
  }

  BlobStorageContext context_;
  scoped_ptr<BlobDataHandle> blob_handle_;
  MockFileStreamReaderProvider* provider_ = nullptr;
  base::MessageLoop message_loop_;
  scoped_ptr<BlobReader> reader_;

 private:
  DISALLOW_COPY_AND_ASSIGN(BlobReaderTest);
};

namespace {

TEST_F(BlobReaderTest, BasicMemory) {
  BlobDataBuilder b("uuid");
  const std::string kData("Hello!!!");
  const size_t kDataSize = 8ul;
  b.AppendData(kData);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kDataSize, size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kDataSize));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kDataSize, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kDataSize, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "Hello!!!", kDataSize));
}

TEST_F(BlobReaderTest, BasicFile) {
  BlobDataBuilder b("uuid");
  const FilePath kPath = FilePath::FromUTF8Unsafe("/fake/file.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();
  b.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&b);

  // Non-async reader.
  ExpectLocalFileCall(kPath, kTime, 0, new FakeFileStreamReader(kData));

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kData.size(), static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "FileData!!!", kData.size()));
}

TEST_F(BlobReaderTest, BasicFileSystem) {
  BlobDataBuilder b("uuid");
  const GURL kURL("file://test_file/here.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();
  b.AppendFileSystemFile(kURL, 0, kData.size(), kTime);
  this->InitializeReader(&b);

  // Non-async reader.
  ExpectFileSystemCall(kURL, 0, kData.size(), kTime,
                       new FakeFileStreamReader(kData));

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kData.size(), static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "FileData!!!", kData.size()));
}

TEST_F(BlobReaderTest, BasicDiskCache) {
  scoped_ptr<disk_cache::Backend> cache =
      CreateInMemoryDiskCache(message_loop_.task_runner());
  ASSERT_TRUE(cache);

  BlobDataBuilder b("uuid");
  const std::string kData = "Test Blob Data";
  scoped_refptr<BlobDataBuilder::DataHandle> data_handle =
      new EmptyDataHandle();
  disk_cache::ScopedEntryPtr entry =
      CreateDiskCacheEntry(cache.get(), "test entry", kData);
  b.AppendDiskCacheEntry(data_handle, entry.get(), kTestDiskCacheStreamIndex);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kData.size(), static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "Test Blob Data", kData.size()));
}

TEST_F(BlobReaderTest, BufferLargerThanMemory) {
  BlobDataBuilder b("uuid");
  const std::string kData("Hello!!!");
  const size_t kDataSize = 8ul;
  const size_t kBufferSize = 10ul;
  b.AppendData(kData);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kBufferSize));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kBufferSize, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kDataSize, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "Hello!!!", kDataSize));
}

TEST_F(BlobReaderTest, MemoryRange) {
  BlobDataBuilder b("uuid");
  const std::string kData("Hello!!!");
  const size_t kDataSize = 8ul;
  const size_t kSeekOffset = 2ul;
  const uint64_t kReadLength = 4ull;
  b.AppendData(kData);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(kReadLength);

  reader_->SetReadRange(kSeekOffset, kReadLength);
  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kDataSize - kSeekOffset, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kReadLength, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "llo!", kReadLength));
}

TEST_F(BlobReaderTest, BufferSmallerThanMemory) {
  BlobDataBuilder b("uuid");
  const std::string kData("Hello!!!");
  const size_t kBufferSize = 4ul;
  b.AppendData(kData);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kBufferSize));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kBufferSize, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kBufferSize, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "Hell", kBufferSize));

  bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kBufferSize, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kBufferSize, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "o!!!", kBufferSize));
}

TEST_F(BlobReaderTest, SegmentedBufferAndMemory) {
  BlobDataBuilder b("uuid");
  const size_t kNumItems = 10;
  const size_t kItemSize = 6;
  const size_t kBufferSize = 10;
  const size_t kTotalSize = kNumItems * kItemSize;
  char current_value = 0;
  for (size_t i = 0; i < kNumItems; i++) {
    char buf[kItemSize];
    for (size_t j = 0; j < kItemSize; j++) {
      buf[j] = current_value++;
    }
    b.AppendData(buf, kItemSize);
  }
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kTotalSize, size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kBufferSize));

  current_value = 0;
  for (size_t i = 0; i < kTotalSize / kBufferSize; i++) {
    int bytes_read = 0;
    int async_bytes_read = 0;
    EXPECT_EQ(BlobReader::Status::DONE,
              reader_->Read(buffer.get(), kBufferSize, &bytes_read,
                            base::Bind(&SetValue<int>, &async_bytes_read)));
    EXPECT_EQ(net::OK, reader_->net_error());
    EXPECT_EQ(kBufferSize, static_cast<size_t>(bytes_read));
    EXPECT_EQ(0, async_bytes_read);
    for (size_t j = 0; j < kBufferSize; j++) {
      EXPECT_EQ(current_value, buffer->data()[j]);
      current_value++;
    }
  }
}

TEST_F(BlobReaderTest, FileAsync) {
  BlobDataBuilder b("uuid");
  const FilePath kPath = FilePath::FromUTF8Unsafe("/fake/file.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();
  b.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&b);

  scoped_ptr<FakeFileStreamReader> reader(new FakeFileStreamReader(kData));
  reader->SetAsyncRunner(message_loop_.task_runner().get());

  ExpectLocalFileCall(kPath, kTime, 0, reader.release());

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeNotCalculatedYet(size_result);
  message_loop_.RunUntilIdle();
  CheckSizeCalculatedAsynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kData.size(), static_cast<size_t>(async_bytes_read));
  EXPECT_EQ(0, bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "FileData!!!", kData.size()));
}

TEST_F(BlobReaderTest, FileSystemAsync) {
  BlobDataBuilder b("uuid");
  const GURL kURL("file://test_file/here.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();
  b.AppendFileSystemFile(kURL, 0, kData.size(), kTime);
  this->InitializeReader(&b);

  scoped_ptr<FakeFileStreamReader> reader(new FakeFileStreamReader(kData));
  reader->SetAsyncRunner(message_loop_.task_runner().get());

  ExpectFileSystemCall(kURL, 0, kData.size(), kTime, reader.release());

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeNotCalculatedYet(size_result);
  message_loop_.RunUntilIdle();
  CheckSizeCalculatedAsynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kData.size(), static_cast<size_t>(async_bytes_read));
  EXPECT_EQ(0, bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "FileData!!!", kData.size()));
}

TEST_F(BlobReaderTest, DiskCacheAsync) {
  scoped_ptr<disk_cache::Backend> cache =
      CreateInMemoryDiskCache(message_loop_.task_runner());
  ASSERT_TRUE(cache);

  BlobDataBuilder b("uuid");
  const std::string kData = "Test Blob Data";
  scoped_refptr<BlobDataBuilder::DataHandle> data_handle =
      new EmptyDataHandle();
  scoped_ptr<DelayedReadEntry> delayed_read_entry(new DelayedReadEntry(
      CreateDiskCacheEntry(cache.get(), "test entry", kData)));
  b.AppendDiskCacheEntry(data_handle, delayed_read_entry.get(),
                         kTestDiskCacheStreamIndex);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeCalculatedSynchronously(kData.size(), size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_TRUE(delayed_read_entry->HasPendingReadCallbacks());
  delayed_read_entry->RunPendingReadCallbacks();
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(0, bytes_read);
  EXPECT_EQ(kData.size(), static_cast<size_t>(async_bytes_read));
  EXPECT_EQ(0, memcmp(buffer->data(), "Test Blob Data", kData.size()));
}

TEST_F(BlobReaderTest, FileRange) {
  BlobDataBuilder b("uuid");
  const FilePath kPath = FilePath::FromUTF8Unsafe("/fake/file.txt");
  // We check the offset in the ExpectLocalFileCall mock.
  const std::string kRangeData = "leD";
  const std::string kData = "FileData!!!";
  const uint64_t kOffset = 2;
  const uint64_t kReadLength = 3;
  const base::Time kTime = base::Time::Now();
  b.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&b);

  scoped_ptr<FakeFileStreamReader> reader(new FakeFileStreamReader(kData));
  reader->SetAsyncRunner(message_loop_.task_runner().get());
  ExpectLocalFileCall(kPath, kTime, 0, reader.release());

  // We create the reader again with the offset after the seek.
  reader.reset(new FakeFileStreamReader(kRangeData));
  reader->SetAsyncRunner(message_loop_.task_runner().get());
  ExpectLocalFileCall(kPath, kTime, kOffset, reader.release());

  int size_result = -1;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  message_loop_.RunUntilIdle();

  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(kReadLength);
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->SetReadRange(kOffset, kReadLength));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kReadLength, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kReadLength, static_cast<size_t>(async_bytes_read));
  EXPECT_EQ(0, bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "leD", kReadLength));
}

TEST_F(BlobReaderTest, DiskCacheRange) {
  scoped_ptr<disk_cache::Backend> cache =
      CreateInMemoryDiskCache(message_loop_.task_runner());
  ASSERT_TRUE(cache);

  BlobDataBuilder b("uuid");
  const std::string kData = "Test Blob Data";
  const uint64_t kOffset = 2;
  const uint64_t kReadLength = 3;
  scoped_refptr<BlobDataBuilder::DataHandle> data_handle =
      new EmptyDataHandle();
  disk_cache::ScopedEntryPtr entry =
      CreateDiskCacheEntry(cache.get(), "test entry", kData);
  b.AppendDiskCacheEntry(data_handle, entry.get(), kTestDiskCacheStreamIndex);
  this->InitializeReader(&b);

  int size_result = -1;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));

  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(kReadLength);
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->SetReadRange(kOffset, kReadLength));

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->Read(buffer.get(), kReadLength, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(kReadLength, static_cast<size_t>(bytes_read));
  EXPECT_EQ(0, async_bytes_read);
  EXPECT_EQ(0, memcmp(buffer->data(), "st ", kReadLength));
}

TEST_F(BlobReaderTest, FileSomeAsyncSegmentedOffsetsUnknownSizes) {
  // This tests includes:
  // * Unknown file sizes (item length of uint64_t::max) for every other item.
  // * Offsets for every 3rd file item.
  // * Non-async reader for every 4th file item.
  BlobDataBuilder b("uuid");
  const FilePath kPathBase = FilePath::FromUTF8Unsafe("/fake/file.txt");
  const base::Time kTime = base::Time::Now();
  const size_t kNumItems = 10;
  const size_t kItemSize = 6;
  const size_t kBufferSize = 10;
  const size_t kTotalSize = kNumItems * kItemSize;
  char current_value = 0;
  // Create blob and reader.
  for (size_t i = 0; i < kNumItems; i++) {
    current_value += kItemSize;
    FilePath path = kPathBase.Append(
        FilePath::FromUTF8Unsafe(base::StringPrintf("%d", current_value)));
    uint64_t offset = i % 3 == 0 ? 1 : 0;
    uint64_t size =
        i % 2 == 0 ? kItemSize : std::numeric_limits<uint64_t>::max();
    b.AppendFile(path, offset, size, kTime);
  }
  this->InitializeReader(&b);

  // Set expectations.
  current_value = 0;
  for (size_t i = 0; i < kNumItems; i++) {
    uint64_t offset = i % 3 == 0 ? 1 : 0;
    scoped_ptr<char[]> buf(new char[kItemSize + offset]);
    if (offset > 0) {
      memset(buf.get(), 7, offset);
    }
    for (size_t j = 0; j < kItemSize; j++) {
      buf.get()[j + offset] = current_value++;
    }
    scoped_ptr<FakeFileStreamReader> reader(new FakeFileStreamReader(
        std::string(buf.get() + offset, kItemSize), kItemSize + offset));
    if (i % 4 != 0) {
      reader->SetAsyncRunner(message_loop_.task_runner().get());
    }
    FilePath path = kPathBase.Append(
        FilePath::FromUTF8Unsafe(base::StringPrintf("%d", current_value)));
    ExpectLocalFileCall(path, kTime, offset, reader.release());
  }

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeNotCalculatedYet(size_result);
  message_loop_.RunUntilIdle();
  CheckSizeCalculatedAsynchronously(kTotalSize, size_result);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kBufferSize));

  current_value = 0;
  for (size_t i = 0; i < kTotalSize / kBufferSize; i++) {
    int bytes_read = 0;
    int async_bytes_read = 0;
    EXPECT_EQ(BlobReader::Status::IO_PENDING,
              reader_->Read(buffer.get(), kBufferSize, &bytes_read,
                            base::Bind(&SetValue<int>, &async_bytes_read)));
    message_loop_.RunUntilIdle();
    EXPECT_EQ(net::OK, reader_->net_error());
    EXPECT_EQ(0, bytes_read);
    EXPECT_EQ(kBufferSize, static_cast<size_t>(async_bytes_read));
    for (size_t j = 0; j < kBufferSize; j++) {
      EXPECT_EQ(current_value, buffer->data()[j]);
      current_value++;
    }
  }
}

TEST_F(BlobReaderTest, MixedContent) {
  // Includes data, a file, and a disk cache entry.
  scoped_ptr<disk_cache::Backend> cache =
      CreateInMemoryDiskCache(message_loop_.task_runner());
  ASSERT_TRUE(cache);

  BlobDataBuilder b("uuid");
  const std::string kData1("Hello ");
  const std::string kData2("there. ");
  const std::string kData3("This ");
  const std::string kData4("is multi-content.");
  const uint64_t kDataSize = 35;

  const base::Time kTime = base::Time::Now();
  const FilePath kData1Path = FilePath::FromUTF8Unsafe("/fake/file.txt");

  disk_cache::ScopedEntryPtr entry3 =
      CreateDiskCacheEntry(cache.get(), "test entry", kData3);

  b.AppendFile(kData1Path, 0, kData1.size(), kTime);
  b.AppendData(kData2);
  b.AppendDiskCacheEntry(
      scoped_refptr<BlobDataBuilder::DataHandle>(new EmptyDataHandle()),
      entry3.get(), kTestDiskCacheStreamIndex);
  b.AppendData(kData4);

  this->InitializeReader(&b);

  scoped_ptr<FakeFileStreamReader> reader(new FakeFileStreamReader(kData1));
  reader->SetAsyncRunner(message_loop_.task_runner().get());
  ExpectLocalFileCall(kData1Path, kTime, 0, reader.release());

  int size_result = -1;
  EXPECT_FALSE(IsReaderTotalSizeCalculated());
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  CheckSizeNotCalculatedYet(size_result);
  message_loop_.RunUntilIdle();
  CheckSizeCalculatedAsynchronously(kDataSize, size_result);

  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(kDataSize);

  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kDataSize, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(0, async_bytes_read);
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::OK, reader_->net_error());
  EXPECT_EQ(0, bytes_read);
  EXPECT_EQ(kDataSize, static_cast<size_t>(async_bytes_read));
  EXPECT_EQ(0, memcmp(buffer->data(), "Hello there. This is multi-content.",
                      kDataSize));
}

TEST_F(BlobReaderTest, StateErrors) {
  // Test common variables
  int bytes_read = -1;
  int async_bytes_read = -1;
  int size_result = -1;
  const std::string kData("Hello!!!");

  // Case: Blob handle is a nullptr.
  InitializeReader(nullptr);
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());
  EXPECT_EQ(BlobReader::Status::NET_ERROR, reader_->SetReadRange(0, 10));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());
  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(10);
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->Read(buffer.get(), 10, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());

  // Case: Not calling CalculateSize before SetReadRange.
  BlobDataBuilder builder1("uuid1");
  builder1.AppendData(kData);
  InitializeReader(&builder1);
  EXPECT_EQ(BlobReader::Status::NET_ERROR, reader_->SetReadRange(0, 10));
  EXPECT_EQ(net::ERR_FAILED, reader_->net_error());
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->Read(buffer.get(), 10, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));

  // Case: Not calling CalculateSize before Read.
  BlobDataBuilder builder2("uuid2");
  builder2.AppendData(kData);
  InitializeReader(&builder2);
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->Read(buffer.get(), 10, &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
}

TEST_F(BlobReaderTest, FileErrorsSync) {
  int size_result = -1;
  const FilePath kPath = FilePath::FromUTF8Unsafe("/fake/file.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();

  // Case: Error on length query.
  BlobDataBuilder builder1("uuid1");
  builder1.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&builder1);
  FakeFileStreamReader* reader = new FakeFileStreamReader(kData);
  reader->SetReturnError(net::ERR_FILE_NOT_FOUND);
  ExpectLocalFileCall(kPath, kTime, 0, reader);

  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());

  // Case: Error on read.
  BlobDataBuilder builder2("uuid2");
  builder2.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&builder2);
  reader = new FakeFileStreamReader(kData);
  ExpectLocalFileCall(kPath, kTime, 0, reader);
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  reader->SetReturnError(net::ERR_FILE_NOT_FOUND);

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));
  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());
}

TEST_F(BlobReaderTest, FileErrorsAsync) {
  int size_result = -1;
  const FilePath kPath = FilePath::FromUTF8Unsafe("/fake/file.txt");
  const std::string kData = "FileData!!!";
  const base::Time kTime = base::Time::Now();

  // Case: Error on length query.
  BlobDataBuilder builder1("uuid1");
  builder1.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&builder1);
  FakeFileStreamReader* reader = new FakeFileStreamReader(kData);
  reader->SetAsyncRunner(message_loop_.task_runner().get());
  reader->SetReturnError(net::ERR_FILE_NOT_FOUND);
  ExpectLocalFileCall(kPath, kTime, 0, reader);

  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  EXPECT_EQ(net::OK, reader_->net_error());
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, size_result);
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());

  // Case: Error on read.
  BlobDataBuilder builder2("uuid2");
  builder2.AppendFile(kPath, 0, kData.size(), kTime);
  this->InitializeReader(&builder2);
  reader = new FakeFileStreamReader(kData);
  ExpectLocalFileCall(kPath, kTime, 0, reader);
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  reader->SetReturnError(net::ERR_FILE_NOT_FOUND);
  reader->SetAsyncRunner(message_loop_.task_runner().get());

  scoped_refptr<net::IOBuffer> buffer(new net::IOBuffer(kData.size()));
  int bytes_read = 0;
  int async_bytes_read = 0;
  EXPECT_EQ(BlobReader::Status::IO_PENDING,
            reader_->Read(buffer.get(), kData.size(), &bytes_read,
                          base::Bind(&SetValue<int>, &async_bytes_read)));
  EXPECT_EQ(net::OK, reader_->net_error());
  message_loop_.RunUntilIdle();
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, async_bytes_read);
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());
}

TEST_F(BlobReaderTest, RangeError) {
  const std::string kData("Hello!!!");
  const size_t kDataSize = 8ul;
  const uint64_t kReadLength = 4ull;

  // Case: offset too high.
  BlobDataBuilder b("uuid1");
  b.AppendData(kData);
  this->InitializeReader(&b);
  int size_result = -1;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  scoped_refptr<net::IOBuffer> buffer = CreateBuffer(kDataSize);
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->SetReadRange(kDataSize + 1, kReadLength));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());

  // Case: length too long.
  BlobDataBuilder b2("uuid2");
  b2.AppendData(kData);
  this->InitializeReader(&b2);
  size_result = -1;
  EXPECT_EQ(BlobReader::Status::DONE,
            reader_->CalculateSize(base::Bind(&SetValue<int>, &size_result)));
  buffer = CreateBuffer(kDataSize + 1);
  EXPECT_EQ(BlobReader::Status::NET_ERROR,
            reader_->SetReadRange(0, kDataSize + 1));
  EXPECT_EQ(net::ERR_FILE_NOT_FOUND, reader_->net_error());
}

}  // namespace
}  // namespace storage
