// Copyright 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 "cc/resources/resource_update_controller.h"

#include "base/test/test_simple_task_runner.h"
#include "cc/resources/prioritized_resource_manager.h"
#include "cc/test/fake_output_surface.h"
#include "cc/test/fake_output_surface_client.h"
#include "cc/test/fake_proxy.h"
#include "cc/test/scheduler_test_common.h"
#include "cc/test/test_shared_bitmap_manager.h"
#include "cc/test/test_web_graphics_context_3d.h"
#include "cc/test/tiled_layer_test_common.h"
#include "cc/trees/single_thread_proxy.h"  // For DebugScopedSetImplThread
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/khronos/GLES2/gl2ext.h"

using testing::Test;

namespace cc {
namespace {

const int kFlushPeriodFull = 4;
const int kFlushPeriodPartial = kFlushPeriodFull;

class ResourceUpdateControllerTest;

class WebGraphicsContext3DForUploadTest : public TestWebGraphicsContext3D {
 public:
  explicit WebGraphicsContext3DForUploadTest(ResourceUpdateControllerTest* test)
      : test_(test) {}

  void flush() override;
  void shallowFlushCHROMIUM() override;
  void texSubImage2D(GLenum target,
                     GLint level,
                     GLint xoffset,
                     GLint yoffset,
                     GLsizei width,
                     GLsizei height,
                     GLenum format,
                     GLenum type,
                     const void* pixels) override;

  void getQueryObjectuivEXT(GLuint id, GLenum pname, GLuint* value) override;

 private:
  ResourceUpdateControllerTest* test_;
};

class ResourceUpdateControllerTest : public Test {
 public:
  ResourceUpdateControllerTest()
      : proxy_(),
        queue_(make_scoped_ptr(new ResourceUpdateQueue)),
        resource_manager_(PrioritizedResourceManager::Create(&proxy_)),
        query_results_available_(0),
        full_upload_count_expected_(0),
        partial_count_expected_(0),
        total_upload_count_expected_(0),
        max_upload_count_per_update_(0),
        num_consecutive_flushes_(0),
        num_dangling_uploads_(0),
        num_total_uploads_(0),
        num_total_flushes_(0) {}

  ~ResourceUpdateControllerTest() override {
    DebugScopedSetImplThreadAndMainThreadBlocked
    impl_thread_and_main_thread_blocked(&proxy_);
    resource_manager_->ClearAllMemory(resource_provider_.get());
  }

 public:
  void OnFlush() {
    // Check for back-to-back flushes.
    EXPECT_EQ(0, num_consecutive_flushes_) << "Back-to-back flushes detected.";

    num_dangling_uploads_ = 0;
    num_consecutive_flushes_++;
    num_total_flushes_++;
  }

  void OnUpload() {
    // Check for too many consecutive uploads
    if (num_total_uploads_ < full_upload_count_expected_) {
      EXPECT_LT(num_dangling_uploads_, kFlushPeriodFull)
          << "Too many consecutive full uploads detected.";
    } else {
      EXPECT_LT(num_dangling_uploads_, kFlushPeriodPartial)
          << "Too many consecutive partial uploads detected.";
    }

    num_consecutive_flushes_ = 0;
    num_dangling_uploads_++;
    num_total_uploads_++;
  }

  bool IsQueryResultAvailable() {
    if (!query_results_available_)
      return false;

    query_results_available_--;
    return true;
  }

 protected:
  void SetUp() override {
    bitmap_.allocN32Pixels(300, 150);

    for (int i = 0; i < 4; i++) {
      textures_[i] = PrioritizedResource::Create(resource_manager_.get(),
                                                 gfx::Size(300, 150),
                                                 RGBA_8888);
      textures_[i]->
          set_request_priority(PriorityCalculator::VisiblePriority(true));
    }
    resource_manager_->PrioritizeTextures();

    output_surface_ = FakeOutputSurface::Create3d(
        scoped_ptr<TestWebGraphicsContext3D>(
            new WebGraphicsContext3DForUploadTest(this)));
    CHECK(output_surface_->BindToClient(&output_surface_client_));

    shared_bitmap_manager_.reset(new TestSharedBitmapManager());
    resource_provider_ = ResourceProvider::Create(output_surface_.get(),
                                                  shared_bitmap_manager_.get(),
                                                  NULL,
                                                  NULL,
                                                  0,
                                                  false,
                                                  1);
  }

  void AppendFullUploadsOfIndexedTextureToUpdateQueue(int count,
                                                      int texture_index) {
    full_upload_count_expected_ += count;
    total_upload_count_expected_ += count;

    const gfx::Rect rect(0, 0, 300, 150);
    const ResourceUpdate upload = ResourceUpdate::Create(
        textures_[texture_index].get(), &bitmap_, rect, rect, gfx::Vector2d());
    for (int i = 0; i < count; i++)
      queue_->AppendFullUpload(upload);
  }

  void AppendFullUploadsToUpdateQueue(int count) {
    AppendFullUploadsOfIndexedTextureToUpdateQueue(count, 0);
  }

  void AppendPartialUploadsOfIndexedTextureToUpdateQueue(int count,
                                                         int texture_index) {
    partial_count_expected_ += count;
    total_upload_count_expected_ += count;

    const gfx::Rect rect(0, 0, 100, 100);
    const ResourceUpdate upload = ResourceUpdate::Create(
        textures_[texture_index].get(), &bitmap_, rect, rect, gfx::Vector2d());
    for (int i = 0; i < count; i++)
      queue_->AppendPartialUpload(upload);
  }

  void AppendPartialUploadsToUpdateQueue(int count) {
    AppendPartialUploadsOfIndexedTextureToUpdateQueue(count, 0);
  }

  void SetMaxUploadCountPerUpdate(int count) {
    max_upload_count_per_update_ = count;
  }

  void UpdateTextures() {
    DebugScopedSetImplThreadAndMainThreadBlocked
    impl_thread_and_main_thread_blocked(&proxy_);
    scoped_ptr<ResourceUpdateController> update_controller =
        ResourceUpdateController::Create(NULL,
                                         proxy_.ImplThreadTaskRunner(),
                                         queue_.Pass(),
                                         resource_provider_.get());
    update_controller->Finalize();
  }

  void MakeQueryResultAvailable() { query_results_available_++; }

 protected:
  // Classes required to interact and test the ResourceUpdateController
  FakeProxy proxy_;
  FakeOutputSurfaceClient output_surface_client_;
  scoped_ptr<OutputSurface> output_surface_;
  scoped_ptr<SharedBitmapManager> shared_bitmap_manager_;
  scoped_ptr<ResourceProvider> resource_provider_;
  scoped_ptr<ResourceUpdateQueue> queue_;
  scoped_ptr<PrioritizedResource> textures_[4];
  scoped_ptr<PrioritizedResourceManager> resource_manager_;
  SkBitmap bitmap_;
  int query_results_available_;

  // Properties / expectations of this test
  int full_upload_count_expected_;
  int partial_count_expected_;
  int total_upload_count_expected_;
  int max_upload_count_per_update_;

  // Dynamic properties of this test
  int num_consecutive_flushes_;
  int num_dangling_uploads_;
  int num_total_uploads_;
  int num_total_flushes_;
};

void WebGraphicsContext3DForUploadTest::flush() { test_->OnFlush(); }

void WebGraphicsContext3DForUploadTest::shallowFlushCHROMIUM() {
  test_->OnFlush();
}

void WebGraphicsContext3DForUploadTest::texSubImage2D(GLenum target,
                                                      GLint level,
                                                      GLint xoffset,
                                                      GLint yoffset,
                                                      GLsizei width,
                                                      GLsizei height,
                                                      GLenum format,
                                                      GLenum type,
                                                      const void* pixels) {
  test_->OnUpload();
}

void WebGraphicsContext3DForUploadTest::getQueryObjectuivEXT(GLuint id,
                                                             GLenum pname,
                                                             GLuint* params) {
  if (pname == GL_QUERY_RESULT_AVAILABLE_EXT)
    *params = test_->IsQueryResultAvailable();
}

// ZERO UPLOADS TESTS
TEST_F(ResourceUpdateControllerTest, ZeroUploads) {
  AppendFullUploadsToUpdateQueue(0);
  AppendPartialUploadsToUpdateQueue(0);
  UpdateTextures();

  EXPECT_EQ(0, num_total_flushes_);
  EXPECT_EQ(0, num_total_uploads_);
}

// ONE UPLOAD TESTS
TEST_F(ResourceUpdateControllerTest, OneFullUpload) {
  AppendFullUploadsToUpdateQueue(1);
  AppendPartialUploadsToUpdateQueue(0);
  UpdateTextures();

  EXPECT_EQ(1, num_total_flushes_);
  EXPECT_EQ(1, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

TEST_F(ResourceUpdateControllerTest, OnePartialUpload) {
  AppendFullUploadsToUpdateQueue(0);
  AppendPartialUploadsToUpdateQueue(1);
  UpdateTextures();

  EXPECT_EQ(1, num_total_flushes_);
  EXPECT_EQ(1, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

TEST_F(ResourceUpdateControllerTest, OneFullOnePartialUpload) {
  AppendFullUploadsToUpdateQueue(1);
  AppendPartialUploadsToUpdateQueue(1);
  UpdateTextures();

  EXPECT_EQ(1, num_total_flushes_);
  EXPECT_EQ(2, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

// This class of tests upload a number of textures that is a multiple
// of the flush period.
const int full_upload_flush_multipler = 7;
const int full_count = full_upload_flush_multipler * kFlushPeriodFull;

const int partial_upload_flush_multipler = 11;
const int partial_count =
    partial_upload_flush_multipler * kFlushPeriodPartial;

TEST_F(ResourceUpdateControllerTest, ManyFullUploads) {
  AppendFullUploadsToUpdateQueue(full_count);
  AppendPartialUploadsToUpdateQueue(0);
  UpdateTextures();

  EXPECT_EQ(full_upload_flush_multipler, num_total_flushes_);
  EXPECT_EQ(full_count, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

TEST_F(ResourceUpdateControllerTest, ManyPartialUploads) {
  AppendFullUploadsToUpdateQueue(0);
  AppendPartialUploadsToUpdateQueue(partial_count);
  UpdateTextures();

  EXPECT_EQ(partial_upload_flush_multipler, num_total_flushes_);
  EXPECT_EQ(partial_count, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

TEST_F(ResourceUpdateControllerTest, ManyFullManyPartialUploads) {
  AppendFullUploadsToUpdateQueue(full_count);
  AppendPartialUploadsToUpdateQueue(partial_count);
  UpdateTextures();

  EXPECT_EQ(full_upload_flush_multipler + partial_upload_flush_multipler,
            num_total_flushes_);
  EXPECT_EQ(full_count + partial_count, num_total_uploads_);
  EXPECT_EQ(0, num_dangling_uploads_)
      << "Last upload wasn't followed by a flush.";
}

class FakeResourceUpdateControllerClient
    : public ResourceUpdateControllerClient {
 public:
  FakeResourceUpdateControllerClient() { Reset(); }
  void Reset() { ready_to_finalize_called_ = false; }
  bool ReadyToFinalizeCalled() const { return ready_to_finalize_called_; }

  void ReadyToFinalizeTextureUpdates() override {
    ready_to_finalize_called_ = true;
  }

 protected:
  bool ready_to_finalize_called_;
};

class FakeResourceUpdateController : public ResourceUpdateController {
 public:
  static scoped_ptr<FakeResourceUpdateController> Create(
      ResourceUpdateControllerClient* client,
      base::TestSimpleTaskRunner* task_runner,
      scoped_ptr<ResourceUpdateQueue> queue,
      ResourceProvider* resource_provider) {
    return make_scoped_ptr(new FakeResourceUpdateController(
        client, task_runner, queue.Pass(), resource_provider));
  }

  void SetNow(base::TimeTicks time) { now_ = time; }
  base::TimeTicks Now() const { return now_; }
  void SetUpdateTextureTime(base::TimeDelta time) {
    update_textures_time_ = time;
  }
  base::TimeTicks UpdateMoreTexturesCompletionTime() override {
    size_t total_updates =
        resource_provider_->NumBlockingUploads() + update_more_textures_size_;
    return now_ + total_updates * update_textures_time_;
  }
  void SetUpdateMoreTexturesSize(size_t size) {
    update_more_textures_size_ = size;
  }
  size_t UpdateMoreTexturesSize() const override {
    return update_more_textures_size_;
  }

 protected:
  FakeResourceUpdateController(ResourceUpdateControllerClient* client,
                               base::TestSimpleTaskRunner* task_runner,
                               scoped_ptr<ResourceUpdateQueue> queue,
                               ResourceProvider* resource_provider)
      : ResourceUpdateController(
          client, task_runner, queue.Pass(), resource_provider),
        resource_provider_(resource_provider),
        update_more_textures_size_(0) {}

  ResourceProvider* resource_provider_;
  base::TimeTicks now_;
  base::TimeDelta update_textures_time_;
  size_t update_more_textures_size_;
};

static void RunPendingTask(base::TestSimpleTaskRunner* task_runner,
                           FakeResourceUpdateController* controller) {
  EXPECT_TRUE(task_runner->HasPendingTask());
  controller->SetNow(controller->Now() + task_runner->NextPendingTaskDelay());
  task_runner->RunPendingTasks();
}

TEST_F(ResourceUpdateControllerTest, UpdateMoreTextures) {
  FakeResourceUpdateControllerClient client;
  scoped_refptr<base::TestSimpleTaskRunner> task_runner =
      new base::TestSimpleTaskRunner;

  SetMaxUploadCountPerUpdate(1);
  AppendFullUploadsToUpdateQueue(3);
  AppendPartialUploadsToUpdateQueue(0);

  DebugScopedSetImplThreadAndMainThreadBlocked
  impl_thread_and_main_thread_blocked(&proxy_);
  scoped_ptr<FakeResourceUpdateController> controller(
      FakeResourceUpdateController::Create(&client,
                                           task_runner.get(),
                                           queue_.Pass(),
                                           resource_provider_.get()));

  controller->SetNow(controller->Now() + base::TimeDelta::FromMilliseconds(1));
  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(100));
  controller->SetUpdateMoreTexturesSize(1);
  // Not enough time for any updates.
  controller->PerformMoreUpdates(controller->Now() +
                                 base::TimeDelta::FromMilliseconds(90));
  EXPECT_FALSE(task_runner->HasPendingTask());

  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(100));
  controller->SetUpdateMoreTexturesSize(1);
  // Only enough time for 1 update.
  controller->PerformMoreUpdates(controller->Now() +
                                 base::TimeDelta::FromMilliseconds(120));
  EXPECT_FALSE(task_runner->HasPendingTask());
  EXPECT_EQ(1, num_total_uploads_);

  // Complete one upload.
  MakeQueryResultAvailable();

  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(100));
  controller->SetUpdateMoreTexturesSize(1);
  // Enough time for 2 updates.
  controller->PerformMoreUpdates(controller->Now() +
                                 base::TimeDelta::FromMilliseconds(220));
  RunPendingTask(task_runner.get(), controller.get());
  EXPECT_FALSE(task_runner->HasPendingTask());
  EXPECT_TRUE(client.ReadyToFinalizeCalled());
  EXPECT_EQ(3, num_total_uploads_);
}

TEST_F(ResourceUpdateControllerTest, NoMoreUpdates) {
  FakeResourceUpdateControllerClient client;
  scoped_refptr<base::TestSimpleTaskRunner> task_runner =
      new base::TestSimpleTaskRunner;

  SetMaxUploadCountPerUpdate(1);
  AppendFullUploadsToUpdateQueue(2);
  AppendPartialUploadsToUpdateQueue(0);

  DebugScopedSetImplThreadAndMainThreadBlocked
  impl_thread_and_main_thread_blocked(&proxy_);
  scoped_ptr<FakeResourceUpdateController> controller(
      FakeResourceUpdateController::Create(&client,
                                           task_runner.get(),
                                           queue_.Pass(),
                                           resource_provider_.get()));

  controller->SetNow(controller->Now() + base::TimeDelta::FromMilliseconds(1));
  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(100));
  controller->SetUpdateMoreTexturesSize(1);
  // Enough time for 3 updates but only 2 necessary.
  controller->PerformMoreUpdates(controller->Now() +
                                 base::TimeDelta::FromMilliseconds(310));
  RunPendingTask(task_runner.get(), controller.get());
  EXPECT_FALSE(task_runner->HasPendingTask());
  EXPECT_TRUE(client.ReadyToFinalizeCalled());
  EXPECT_EQ(2, num_total_uploads_);

  client.Reset();
  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(100));
  controller->SetUpdateMoreTexturesSize(1);
  // Enough time for updates but no more updates left.
  controller->PerformMoreUpdates(controller->Now() +
                                 base::TimeDelta::FromMilliseconds(310));

  // ReadyToFinalizeTextureUpdates should only be called once.
  EXPECT_FALSE(task_runner->HasPendingTask());
  EXPECT_FALSE(client.ReadyToFinalizeCalled());
  EXPECT_EQ(2, num_total_uploads_);
}

TEST_F(ResourceUpdateControllerTest, UpdatesCompleteInFiniteTime) {
  FakeResourceUpdateControllerClient client;
  scoped_refptr<base::TestSimpleTaskRunner> task_runner =
      new base::TestSimpleTaskRunner;

  SetMaxUploadCountPerUpdate(1);
  AppendFullUploadsToUpdateQueue(2);
  AppendPartialUploadsToUpdateQueue(0);

  DebugScopedSetImplThreadAndMainThreadBlocked
  impl_thread_and_main_thread_blocked(&proxy_);
  scoped_ptr<FakeResourceUpdateController> controller(
      FakeResourceUpdateController::Create(&client,
                                           task_runner.get(),
                                           queue_.Pass(),
                                           resource_provider_.get()));

  controller->SetNow(controller->Now() + base::TimeDelta::FromMilliseconds(1));
  controller->SetUpdateTextureTime(base::TimeDelta::FromMilliseconds(500));
  controller->SetUpdateMoreTexturesSize(1);

  for (int i = 0; i < 100; i++) {
    if (client.ReadyToFinalizeCalled())
      break;

    // Not enough time for any updates.
    controller->PerformMoreUpdates(controller->Now() +
                                   base::TimeDelta::FromMilliseconds(400));

    if (task_runner->HasPendingTask())
      RunPendingTask(task_runner.get(), controller.get());
  }

  EXPECT_FALSE(task_runner->HasPendingTask());
  EXPECT_TRUE(client.ReadyToFinalizeCalled());
  EXPECT_EQ(2, num_total_uploads_);
}

}  // namespace
}  // namespace cc
