// Copyright (c) 2012 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 "android_webview/native/input_stream_impl.h" #include "base/android/jni_android.h" #include "base/android/scoped_java_ref.h" #include "base/memory/scoped_ptr.h" #include "jni/InputStreamUnittest_jni.h" #include "net/base/io_buffer.h" #include "net/base/net_errors.h" #include "net/http/http_byte_range.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" using android_webview::InputStream; using android_webview::InputStreamImpl; using base::android::AttachCurrentThread; using base::android::ScopedJavaLocalRef; using net::IOBuffer; using testing::DoAll; using testing::Ge; using testing::InSequence; using testing::Lt; using testing::Ne; using testing::NotNull; using testing::Return; using testing::SetArgPointee; using testing::Test; using testing::_; class InputStreamTest : public Test { public: InputStreamTest() { } protected: void SetUp() override { env_ = AttachCurrentThread(); ASSERT_THAT(env_, NotNull()); ASSERT_TRUE(android_webview::RegisterInputStream(env_)); ASSERT_TRUE(RegisterNativesImpl(env_)); } scoped_refptr DoReadCountedStreamTest(int stream_size, int bytes_requested, int* bytes_read) { ScopedJavaLocalRef counting_jstream = Java_InputStreamUnittest_getCountingStream(env_, stream_size); EXPECT_FALSE(counting_jstream.is_null()); scoped_ptr input_stream( new InputStreamImpl(counting_jstream)); scoped_refptr buffer = new IOBuffer(bytes_requested); EXPECT_TRUE(input_stream->Read(buffer.get(), bytes_requested, bytes_read)); return buffer; } JNIEnv* env_; }; TEST_F(InputStreamTest, ReadEmptyStream) { ScopedJavaLocalRef empty_jstream = Java_InputStreamUnittest_getEmptyStream(env_); EXPECT_FALSE(empty_jstream.is_null()); scoped_ptr input_stream(new InputStreamImpl(empty_jstream)); const int bytes_requested = 10; int bytes_read = 0; scoped_refptr buffer = new IOBuffer(bytes_requested); EXPECT_TRUE(input_stream->Read(buffer.get(), bytes_requested, &bytes_read)); EXPECT_EQ(0, bytes_read); } TEST_F(InputStreamTest, ReadStreamPartial) { const int bytes_requested = 128; int bytes_read = 0; DoReadCountedStreamTest(bytes_requested * 2, bytes_requested, &bytes_read); EXPECT_EQ(bytes_requested, bytes_read); } TEST_F(InputStreamTest, ReadStreamCompletely) { const int bytes_requested = 42; int bytes_read = 0; DoReadCountedStreamTest(bytes_requested, bytes_requested, &bytes_read); EXPECT_EQ(bytes_requested, bytes_read); } TEST_F(InputStreamTest, TryReadMoreThanBuffer) { const int buffer_size = 3 * InputStreamImpl::kBufferSize; int bytes_read = 0; DoReadCountedStreamTest(buffer_size, buffer_size * 2, &bytes_read); EXPECT_EQ(buffer_size, bytes_read); } TEST_F(InputStreamTest, CheckContentsReadCorrectly) { const int bytes_requested = 256; int bytes_read = 0; scoped_refptr buffer = DoReadCountedStreamTest(bytes_requested, bytes_requested, &bytes_read); EXPECT_EQ(bytes_requested, bytes_read); for (int i = 0; i < bytes_requested; ++i) { EXPECT_EQ(i, (unsigned char)buffer->data()[i]); } } TEST_F(InputStreamTest, ReadLargeStreamPartial) { const int bytes_requested = 3 * InputStreamImpl::kBufferSize; int bytes_read = 0; DoReadCountedStreamTest(bytes_requested + 32, bytes_requested, &bytes_read); EXPECT_EQ(bytes_requested, bytes_read); } TEST_F(InputStreamTest, ReadLargeStreamCompletely) { const int bytes_requested = 3 * InputStreamImpl::kBufferSize; int bytes_read = 0; DoReadCountedStreamTest(bytes_requested, bytes_requested, &bytes_read); EXPECT_EQ(bytes_requested, bytes_read); } TEST_F(InputStreamTest, DoesNotCrashWhenExceptionThrown) { ScopedJavaLocalRef throw_jstream = Java_InputStreamUnittest_getThrowingStream(env_); EXPECT_FALSE(throw_jstream.is_null()); scoped_ptr input_stream(new InputStreamImpl(throw_jstream)); int64_t bytes_skipped; EXPECT_FALSE(input_stream->Skip(10, &bytes_skipped)); int bytes_available; EXPECT_FALSE(input_stream->BytesAvailable(&bytes_available)); const int bytes_requested = 10; int bytes_read = 0; scoped_refptr buffer = new IOBuffer(bytes_requested); EXPECT_FALSE(input_stream->Read(buffer.get(), bytes_requested, &bytes_read)); EXPECT_EQ(0, bytes_read); // This closes the stream. input_stream.reset(NULL); }