// Copyright 2014 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 "base/message_loop/message_loop_proxy.h"
#include "cc/layers/solid_color_layer.h"
#include "cc/layers/surface_layer.h"
#include "cc/test/fake_impl_proxy.h"
#include "cc/test/fake_layer_tree_host.h"
#include "cc/test/fake_layer_tree_host_client.h"
#include "cc/test/fake_layer_tree_host_impl.h"
#include "cc/test/fake_output_surface.h"
#include "cc/test/layer_tree_test.h"
#include "cc/test/test_shared_bitmap_manager.h"
#include "cc/trees/layer_tree_host.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace cc {
namespace {

class SurfaceLayerTest : public testing::Test {
 public:
  SurfaceLayerTest()
      : fake_client_(
            FakeLayerTreeHostClient(FakeLayerTreeHostClient::DIRECT_3D)) {}

 protected:
  virtual void SetUp() {
    layer_tree_host_ = FakeLayerTreeHost::Create(&fake_client_);
    layer_tree_host_->SetViewportSize(gfx::Size(10, 10));
  }

  virtual void TearDown() {
    if (layer_tree_host_) {
      layer_tree_host_->SetRootLayer(nullptr);
      layer_tree_host_ = nullptr;
    }
  }

  scoped_ptr<FakeLayerTreeHost> layer_tree_host_;
  FakeLayerTreeHostClient fake_client_;
  TestSharedBitmapManager shared_bitmap_manager_;
};

void SatisfyCallback(SurfaceSequence* out, SurfaceSequence in) {
  *out = in;
}

void RequireCallback(SurfaceId* out_id,
                     std::set<SurfaceSequence>* out,
                     SurfaceId in_id,
                     SurfaceSequence in) {
  *out_id = in_id;
  out->insert(in);
}

// Check that one surface can be referenced by multiple LayerTreeHosts, and
// each will create its own SurfaceSequence that's satisfied on destruction.
TEST_F(SurfaceLayerTest, MultipleFramesOneSurface) {
  SurfaceSequence blank_change;  // Receives sequence if commit doesn't happen.

  SurfaceId required_id;
  std::set<SurfaceSequence> required_seq;
  scoped_refptr<SurfaceLayer> layer(SurfaceLayer::Create(
      base::Bind(&SatisfyCallback, &blank_change),
      base::Bind(&RequireCallback, &required_id, &required_seq)));
  layer->SetSurfaceId(SurfaceId(1));
  layer_tree_host_->set_surface_id_namespace(1);
  layer_tree_host_->SetRootLayer(layer);

  scoped_ptr<FakeLayerTreeHost> layer_tree_host2 =
      FakeLayerTreeHost::Create(&fake_client_);
  scoped_refptr<SurfaceLayer> layer2(SurfaceLayer::Create(
      base::Bind(&SatisfyCallback, &blank_change),
      base::Bind(&RequireCallback, &required_id, &required_seq)));
  layer2->SetSurfaceId(SurfaceId(1));
  layer_tree_host2->set_surface_id_namespace(2);
  layer_tree_host2->SetRootLayer(layer2);

  // Layers haven't been removed, so no sequence should be satisfied.
  EXPECT_TRUE(blank_change.is_null());

  SurfaceSequence expected1(1u, 1u);
  SurfaceSequence expected2(2u, 1u);

  layer_tree_host2->SetRootLayer(nullptr);
  layer_tree_host2.reset();

  // Layer was removed so sequence from second LayerTreeHost should be
  // satisfied.
  EXPECT_TRUE(blank_change == expected2);

  // Set of sequences that need to be satisfied should include sequences from
  // both trees.
  EXPECT_TRUE(required_id == SurfaceId(1));
  EXPECT_EQ(2u, required_seq.size());
  EXPECT_TRUE(required_seq.count(expected1));
  EXPECT_TRUE(required_seq.count(expected2));

  layer_tree_host_->SetRootLayer(nullptr);
  layer_tree_host_.reset();

  // Layer was removed so sequence from first LayerTreeHost should be
  // satisfied.
  EXPECT_TRUE(blank_change == expected1);

  // No more SurfaceSequences should have been generated that need to have be
  // satisfied.
  EXPECT_EQ(2u, required_seq.size());
}

// Check that SurfaceSequence is sent through swap promise.
class SurfaceLayerSwapPromise : public LayerTreeTest {
 public:
  SurfaceLayerSwapPromise()
      : commit_count_(0), sequence_was_satisfied_(false) {}

  void BeginTest() override {
    layer_tree_host()->set_surface_id_namespace(1);
    layer_ = SurfaceLayer::Create(
        base::Bind(&SatisfyCallback, &satisfied_sequence_),
        base::Bind(&RequireCallback, &required_id_, &required_set_));
    layer_->SetSurfaceId(SurfaceId(1));

    // Layer hasn't been added to tree so no SurfaceSequence generated yet.
    EXPECT_EQ(0u, required_set_.size());

    layer_tree_host()->SetRootLayer(layer_);

    // Should have SurfaceSequence from first tree.
    SurfaceSequence expected(1u, 1u);
    EXPECT_TRUE(required_id_ == SurfaceId(1));
    EXPECT_EQ(1u, required_set_.size());
    EXPECT_TRUE(required_set_.count(expected));

    gfx::Size bounds(100, 100);
    layer_tree_host()->SetViewportSize(bounds);
    PostSetNeedsCommitToMainThread();
  }

  void DidCommit() override {
    base::MessageLoopProxy::current()->PostTask(
        FROM_HERE, base::Bind(&SurfaceLayerSwapPromise::ChangeTree,
                              base::Unretained(this)));
  }

  void ChangeTree() {
    ++commit_count_;
    switch (commit_count_) {
      case 1:
        // Remove SurfaceLayer from tree to cause SwapPromise to be created.
        blank_layer_ = SolidColorLayer::Create();
        blank_layer_->SetIsDrawable(true);
        blank_layer_->SetBounds(gfx::Size(10, 10));
        layer_tree_host()->SetRootLayer(blank_layer_);
        break;
      case 2:
        break;
      default:
        NOTREACHED();
        break;
    }
  }

  void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, bool result) override {
    EXPECT_TRUE(result);
    std::vector<uint32_t>& satisfied =
        output_surface()->last_sent_frame().metadata.satisfies_sequences;
    EXPECT_LE(satisfied.size(), 1u);
    if (satisfied.size() == 1) {
      // Eventually the one SurfaceSequence should be satisfied, but only
      // after the layer was removed from the tree, and only once.
      EXPECT_EQ(1u, satisfied[0]);
      EXPECT_LE(1, commit_count_);
      EXPECT_FALSE(sequence_was_satisfied_);
      sequence_was_satisfied_ = true;
      EndTest();
    }
  }

  void AfterTest() override {
    EXPECT_TRUE(required_id_ == SurfaceId(1));
    EXPECT_EQ(1u, required_set_.size());
    // Sequence should have been satisfied through Swap, not with the
    // callback.
    EXPECT_TRUE(satisfied_sequence_.is_null());
  }

 private:
  int commit_count_;
  bool sequence_was_satisfied_;
  scoped_refptr<SurfaceLayer> layer_;
  scoped_refptr<Layer> blank_layer_;
  SurfaceSequence satisfied_sequence_;

  SurfaceId required_id_;
  std::set<SurfaceSequence> required_set_;
};

// TODO(jbauman): Reenable on single thread once http://crbug.com/421923 is
// fixed.
MULTI_THREAD_TEST_F(SurfaceLayerSwapPromise);

}  // namespace
}  // namespace cc
