//
//  Copyright (C) 2015 Google, Inc.
//
//  Licensed under the Apache License, Version 2.0 (the "License");
//  you may not use this file except in compliance with the License.
//  You may obtain a copy of the License at:
//
//  http://www.apache.org/licenses/LICENSE-2.0
//
//  Unless required by applicable law or agreed to in writing, software
//  distributed under the License is distributed on an "AS IS" BASIS,
//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//  See the License for the specific language governing permissions and
//  limitations under the License.
//

#pragma once

#include <base/macros.h>
#include <hardware/bluetooth.h>

namespace bluetooth {
namespace hal {

// This class represents the HAL Bluetooth adapter interface, wrapping around
// the underlying bt_interface_t structure, its methods, and callbacks. A single
// instance of this class exists per application and it allows multiple classes
// to interface with the global HAL interface by multiplexing callbacks among
// registered clients.
//
// This is declared as an abstract interface so that a fake implementation can
// be injected for testing the upper layer.
//
// TODO: (expose callback types directly but via redirection) methods for
// initialize, clean up, and set for testing.
class BluetoothInterface {
 public:
  // The standard Bluetooth adapter management callback interface. The HAL
  // interface doesn't allow registering "user data" that carries context beyond
  // the callback parameters, forcing implementations to deal with global
  // variables. The Observer interface is to redirect these events to interested
  // parties in an object-oriented manner.
  //
  // TODO(armansito): We should fix this in the HAL.
  class Observer {
   public:
    virtual ~Observer() = default;

    // All of the events below correspond to callbacks defined in
    // "bt_callbacks_t" in the HAL API definitions.

    virtual void AdapterStateChangedCallback(bt_state_t state);
    virtual void AdapterPropertiesCallback(bt_status_t status,
                                           int num_properties,
                                           bt_property_t* properties);
    virtual void RemoteDevicePropertiesCallback(bt_status_t status,
                                                RawAddress* remote_bd_addr,
                                                int num_properties,
                                                bt_property_t* properties);
    virtual void DiscoveryStateChangedCallback(bt_discovery_state_t state);
    virtual void PinRequestCallback(RawAddress* remote_bd_addr,
                                    bt_bdname_t* bd_name, uint32_t cod,
                                    bool min_16_digit);
    virtual void SSPRequestCallback(RawAddress* remote_bd_addr,
                                    bt_bdname_t* bd_name, uint32_t cod,
                                    bt_ssp_variant_t pairing_variant,
                                    uint32_t pass_key);
    virtual void BondStateChangedCallback(bt_status_t status,
                                          RawAddress* remote_bd_addr,
                                          bt_bond_state_t state);
    virtual void AclStateChangedCallback(bt_status_t status,
                                         const RawAddress& remote_bdaddr,
                                         bt_acl_state_t state);

    // TODO(armansito): Complete the list of callbacks.
  };

  // Initialize and clean up the BluetoothInterface singleton. Returns false if
  // the underlying HAL interface failed to initialize, and true on success.
  static bool Initialize();

  // Shuts down and cleans up the interface. CleanUp must be called on the same
  // thread that called Initialize.
  static void CleanUp();

  // Returns true if the interface was initialized and a global singleton has
  // been created.
  static bool IsInitialized();

  // Initialize for testing. Use this to inject a test version of
  // BlueoothInterface. To be used from unit tests only.
  static void InitializeForTesting(BluetoothInterface* test_instance);

  // Returns the BluetoothInterface singleton. If the interface has not been
  // initialized, returns nullptr.
  static BluetoothInterface* Get();

  // Add or remove an observer that is interested in notifications from us.
  virtual void AddObserver(Observer* observer) = 0;
  virtual void RemoveObserver(Observer* observer) = 0;

  // The HAL module pointer that represents the standard Bluetooth adapter
  // management interface. This is implemented in and provided by the shared
  // Bluetooth library, so this isn't owned by us.
  //
  // Upper layers can make bt_interface_t API calls through this structure.
  // However, DO NOT call the "init" function as this is called and managed by
  // us. The behavior is undefined if "init" is called directly by upper layers.
  virtual const bt_interface_t* GetHALInterface() const = 0;

  // Returns the HAL callbacks that have been initialized previously.
  virtual bt_callbacks_t* GetHALCallbacks() const = 0;

  // The HAL module pointer that represents the underlying Bluetooth adapter.
  // This is implemented in and provided by the shared Bluetooth library, so
  // this isn't owned by us.
  virtual const bluetooth_device_t* GetHALAdapter() const = 0;

 protected:
  BluetoothInterface() = default;
  virtual ~BluetoothInterface() = default;

 private:
  DISALLOW_COPY_AND_ASSIGN(BluetoothInterface);
};

}  // namespace hal
}  // namespace bluetooth
