// Copyright 2016 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/memory/ref_counted.h"
#include "base/run_loop.h"
#include "chrome/browser/chromeos/login/test/oobe_base_test.h"
#include "chrome/browser/chromeos/login/test/oobe_screen_waiter.h"
#include "chrome/browser/chromeos/login/wizard_controller.h"
#include "chrome/browser/ui/webui/chromeos/login/signin_screen_handler.h"
#include "components/pairing/bluetooth_host_pairing_controller.h"
#include "components/pairing/bluetooth_pairing_constants.h"
#include "components/pairing/shark_connection_listener.h"
#include "content/public/browser/browser_thread.h"
#include "device/bluetooth/bluetooth_device.h"
#include "device/bluetooth/bluez/bluetooth_device_bluez.h"
#include "device/bluetooth/dbus/bluez_dbus_manager.h"
#include "device/bluetooth/dbus/fake_bluetooth_adapter_client.h"
#include "device/bluetooth/dbus/fake_bluetooth_device_client.h"
#include "services/device/public/cpp/hid/fake_input_service_linux.h"
#include "services/device/public/mojom/constants.mojom.h"
#include "services/device/public/mojom/input_service.mojom.h"
#include "services/service_manager/public/cpp/service_binding.h"

namespace chromeos {

namespace {

class TestDelegate
    : public pairing_chromeos::BluetoothHostPairingController::TestDelegate {
 public:
  TestDelegate() {}
  ~TestDelegate() override {}

  // pairing_chromeos::BluetoothHostPairingController::Delegate override:
  void OnAdapterReset() override {
    finished_ = true;
    if (run_loop_)
      run_loop_->Quit();
  }

  void WaitUntilAdapterReset() {
    if (finished_)
      return;
    run_loop_.reset(new base::RunLoop());
    run_loop_->Run();
  }

 private:
  bool finished_ = false;
  std::unique_ptr<base::RunLoop> run_loop_;

  DISALLOW_COPY_AND_ASSIGN(TestDelegate);
};

}  // namespace

// This is the class to simulate the OOBE process for devices that don't have
// sufficient input, i.e., the first screen of OOBE is the HID detection screen.
// The device will put itself in Bluetooth discoverable mode.
class BluetoothHostPairingNoInputTest : public OobeBaseTest {
 public:
  void OnConnectSuccess(base::OnceClosure continuation_callback) {
    std::move(continuation_callback).Run();
  }
  void OnConnectFailed(base::OnceClosure continuation_callback,
                       device::BluetoothDevice::ConnectErrorCode error) {
    std::move(continuation_callback).Run();
  }

 protected:
  using InputDeviceInfoPtr = device::mojom::InputDeviceInfoPtr;

  BluetoothHostPairingNoInputTest() {
    fake_input_service_manager_ =
        std::make_unique<device::FakeInputServiceLinux>();

    service_manager::ServiceBinding::OverrideInterfaceBinderForTesting(
        device::mojom::kServiceName,
        base::Bind(&device::FakeInputServiceLinux::Bind,
                   base::Unretained(fake_input_service_manager_.get())));

    // Set up the fake Bluetooth environment.
    std::unique_ptr<bluez::BluezDBusManagerSetter> bluez_dbus_setter =
        bluez::BluezDBusManager::GetSetterForTesting();
    bluez_dbus_setter->SetBluetoothAdapterClient(
        std::make_unique<bluez::FakeBluetoothAdapterClient>());
    bluez_dbus_setter->SetBluetoothDeviceClient(
        std::make_unique<bluez::FakeBluetoothDeviceClient>());

    // Get pointer.
    fake_bluetooth_device_client_ =
        static_cast<bluez::FakeBluetoothDeviceClient*>(
            bluez::BluezDBusManager::Get()->GetBluetoothDeviceClient());
  }

  ~BluetoothHostPairingNoInputTest() override {
    service_manager::ServiceBinding::ClearInterfaceBinderOverrideForTesting<
        device::mojom::InputDeviceManager>(device::mojom::kServiceName);
  }

  // OobeBaseTest override:
  void SetUpOnMainThread() override {
    OobeBaseTest::SetUpOnMainThread();
    delegate_.reset(new TestDelegate);
    pairing_chromeos::SharkConnectionListener* shark_listener =
        WizardController::default_controller()
            ->GetSharkConnectionListenerForTesting();
    controller_ =
        shark_listener ? shark_listener->GetControllerForTesting() : nullptr;
    if (controller_) {
      controller_->SetDelegateForTesting(delegate_.get());
      bluetooth_adapter_ = controller_->GetAdapterForTesting();
      controller_->SetControllerDeviceAddressForTesting(
          bluez::FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
    }
  }

  pairing_chromeos::BluetoothHostPairingController* controller() {
    return controller_;
  }

  device::BluetoothAdapter* bluetooth_adapter() {
    return bluetooth_adapter_.get();
  }

  TestDelegate* delegate() { return delegate_.get(); }

  bluez::FakeBluetoothDeviceClient* fake_bluetooth_device_client() {
    return fake_bluetooth_device_client_;
  }

  void ResetController() {
    if (controller_)
      controller_->Reset();
  }

  void AddUsbMouse() {
    auto mouse = device::mojom::InputDeviceInfo::New();
    mouse->id = "usb_mouse";
    mouse->subsystem = device::mojom::InputDeviceSubsystem::SUBSYSTEM_INPUT;
    mouse->type = device::mojom::InputDeviceType::TYPE_USB;
    mouse->is_mouse = true;
    fake_input_service_manager_->AddDevice(std::move(mouse));
  }

  void AddUsbKeyboard() {
    auto keyboard = device::mojom::InputDeviceInfo::New();
    keyboard->id = "usb_keyboard";
    keyboard->subsystem = device::mojom::InputDeviceSubsystem::SUBSYSTEM_INPUT;
    keyboard->type = device::mojom::InputDeviceType::TYPE_USB;
    keyboard->is_keyboard = true;
    fake_input_service_manager_->AddDevice(std::move(keyboard));
  }

  void AddBluetoothMouse() {
    auto mouse = device::mojom::InputDeviceInfo::New();
    mouse->id = "bluetooth_mouse";
    mouse->subsystem = device::mojom::InputDeviceSubsystem::SUBSYSTEM_INPUT;
    mouse->type = device::mojom::InputDeviceType::TYPE_BLUETOOTH;
    mouse->is_mouse = true;
    fake_input_service_manager_->AddDevice(std::move(mouse));
  }

 private:
  std::unique_ptr<device::FakeInputServiceLinux> fake_input_service_manager_;
  scoped_refptr<device::BluetoothAdapter> bluetooth_adapter_;
  std::unique_ptr<TestDelegate> delegate_;
  pairing_chromeos::BluetoothHostPairingController* controller_ = nullptr;

  bluez::FakeBluetoothDeviceClient* fake_bluetooth_device_client_ = nullptr;

  DISALLOW_COPY_AND_ASSIGN(BluetoothHostPairingNoInputTest);
};

// Test that in normal user OOBE login flow for devices lacking input devices,
// if there is no Bluetooth device connected, the Bluetooth adapter should be
// disabled when OOBE reaches login screen (which means OOBE has been completed)
IN_PROC_BROWSER_TEST_F(BluetoothHostPairingNoInputTest,
                       NoBluetoothDeviceConnected) {
  OobeScreenWaiter(OobeScreen::SCREEN_OOBE_HID_DETECTION).Wait();
  EXPECT_EQ(bluetooth_adapter()->IsPowered(), true);
  WizardController::default_controller()->SkipToLoginForTesting(
      LoginScreenContext());
  OobeScreenWaiter(OobeScreen::SCREEN_GAIA_SIGNIN).Wait();
  delegate()->WaitUntilAdapterReset();
  EXPECT_EQ(bluetooth_adapter()->IsPowered(), false);
}

// Test that in normal user OOBE login flow for devices lacking input devices,
// if there is any Bluetooth device connected, the Bluetooth adapter should not
// be disabled after OOBE completes.
IN_PROC_BROWSER_TEST_F(BluetoothHostPairingNoInputTest,
                       BluetoothDeviceConnected) {
  OobeScreenWaiter(OobeScreen::SCREEN_OOBE_HID_DETECTION).Wait();
  AddBluetoothMouse();
  EXPECT_EQ(bluetooth_adapter()->IsPowered(), true);
  WizardController::default_controller()->SkipToLoginForTesting(
      LoginScreenContext());
  OobeScreenWaiter(OobeScreen::SCREEN_GAIA_SIGNIN).Wait();
  delegate()->WaitUntilAdapterReset();
  EXPECT_EQ(bluetooth_adapter()->IsPowered(), true);
}

// Test that the paired Master Bluetooth device is disconnected after the
// enrollment is done or failed.
IN_PROC_BROWSER_TEST_F(BluetoothHostPairingNoInputTest, ForgetDevice) {
  OobeScreenWaiter(OobeScreen::SCREEN_OOBE_HID_DETECTION).Wait();
  EXPECT_TRUE(bluetooth_adapter()->IsDiscoverable());
  EXPECT_TRUE(bluetooth_adapter()->IsPowered());

  fake_bluetooth_device_client()->CreateDevice(
      dbus::ObjectPath(bluez::FakeBluetoothAdapterClient::kAdapterPath),
      dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kConfirmPasskeyPath));

  device::BluetoothDevice* device = bluetooth_adapter()->GetDevice(
      bluez::FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
  ASSERT_TRUE(device);
  EXPECT_FALSE(device->IsPaired());
  EXPECT_EQ(3U, bluetooth_adapter()->GetDevices().size());

  base::RunLoop run_loop;
  device->Connect(
      controller(),
      base::Bind(&BluetoothHostPairingNoInputTest::OnConnectSuccess,
                 base::Unretained(this), run_loop.QuitWhenIdleClosure()),
      base::Bind(&BluetoothHostPairingNoInputTest::OnConnectFailed,
                 base::Unretained(this), run_loop.QuitWhenIdleClosure()));
  run_loop.Run();
  EXPECT_TRUE(device->IsPaired());

  ResetController();
  delegate()->WaitUntilAdapterReset();

  // The device should have been removed now.
  EXPECT_TRUE(!bluetooth_adapter()->GetDevice(
      bluez::FakeBluetoothDeviceClient::kConfirmPasskeyAddress));
  EXPECT_EQ(2U, bluetooth_adapter()->GetDevices().size());
  EXPECT_FALSE(bluetooth_adapter()->IsDiscoverable());
  EXPECT_FALSE(bluetooth_adapter()->IsPowered());
}

// This is the class to simulate the OOBE process for devices that have
// sufficient input, i.e., the first screen of OOBE is the welcome screen.
// The device will not put itself in Bluetooth discoverable mode until the user
// manually trigger it using the proper accelerator.
class BluetoothHostPairingWithInputTest
    : public BluetoothHostPairingNoInputTest {
 public:
  BluetoothHostPairingWithInputTest() {
    AddUsbMouse();
    AddUsbKeyboard();
  }
  ~BluetoothHostPairingWithInputTest() override {}

 private:
  DISALLOW_COPY_AND_ASSIGN(BluetoothHostPairingWithInputTest);
};

// Test that in normal user OOBE login flow for devices that have input devices,
// the Bluetooth is disabled by default.
IN_PROC_BROWSER_TEST_F(BluetoothHostPairingWithInputTest,
                       BluetoothDisableByDefault) {
  OobeScreenWaiter(OobeScreen::SCREEN_OOBE_WELCOME).Wait();
  EXPECT_FALSE(controller());
  EXPECT_FALSE(bluetooth_adapter());
}

}  // namespace chromeos
