blob: 23a18c151ca982b20b28252cd2f797e28d434a0e [file] [log] [blame]
// Copyright 2017 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 "device/bluetooth/test/fake_central.h"
#include <memory>
#include <string>
#include <utility>
#include <vector>
#include "device/bluetooth/bluetooth_device.h"
#include "device/bluetooth/bluetooth_discovery_filter.h"
#include "device/bluetooth/bluetooth_uuid.h"
#include "device/bluetooth/public/interfaces/test/fake_bluetooth.mojom.h"
#include "device/bluetooth/test/fake_peripheral.h"
#include "device/bluetooth/test/fake_remote_gatt_characteristic.h"
#include "device/bluetooth/test/fake_remote_gatt_service.h"
namespace bluetooth {
FakeCentral::FakeCentral(mojom::CentralState state,
mojom::FakeCentralRequest request)
: state_(state), binding_(this, std::move(request)) {}
void FakeCentral::SimulatePreconnectedPeripheral(
const std::string& address,
const std::string& name,
const std::vector<device::BluetoothUUID>& known_service_uuids,
SimulatePreconnectedPeripheralCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(address);
if (fake_peripheral == nullptr) {
auto fake_peripheral_ptr = std::make_unique<FakePeripheral>(this, address);
fake_peripheral = fake_peripheral_ptr.get();
auto pair = devices_.emplace(address, std::move(fake_peripheral_ptr));
DCHECK(pair.second);
}
fake_peripheral->SetName(name);
fake_peripheral->SetSystemConnected(true);
fake_peripheral->SetServiceUUIDs(device::BluetoothDevice::UUIDSet(
known_service_uuids.begin(), known_service_uuids.end()));
std::move(callback).Run();
}
void FakeCentral::SetNextGATTConnectionResponse(
const std::string& address,
uint16_t code,
SetNextGATTConnectionResponseCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(address);
if (fake_peripheral == nullptr) {
std::move(callback).Run(false);
return;
}
fake_peripheral->SetNextGATTConnectionResponse(code);
std::move(callback).Run(true);
}
void FakeCentral::SetNextGATTDiscoveryResponse(
const std::string& address,
uint16_t code,
SetNextGATTDiscoveryResponseCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(address);
if (fake_peripheral == nullptr) {
std::move(callback).Run(false);
return;
}
fake_peripheral->SetNextGATTDiscoveryResponse(code);
std::move(callback).Run(true);
}
bool FakeCentral::AllResponsesConsumed() {
return std::all_of(devices_.begin(), devices_.end(), [](const auto& e) {
// static_cast is safe because the parent class's devices_ is only
// populated via this FakeCentral, and only with FakePeripherals.
FakePeripheral* fake_peripheral =
static_cast<FakePeripheral*>(e.second.get());
return fake_peripheral->AllResponsesConsumed();
});
}
void FakeCentral::SimulateGATTDisconnection(
const std::string& address,
SimulateGATTDisconnectionCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(address);
if (fake_peripheral == nullptr) {
std::move(callback).Run(false);
}
fake_peripheral->SimulateGATTDisconnection();
std::move(callback).Run(true);
}
void FakeCentral::SimulateGATTServicesChanged(
const std::string& address,
SimulateGATTServicesChangedCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(address);
if (fake_peripheral == nullptr) {
std::move(callback).Run(false);
return;
}
std::move(callback).Run(true);
}
void FakeCentral::AddFakeService(const std::string& peripheral_address,
const device::BluetoothUUID& service_uuid,
AddFakeServiceCallback callback) {
FakePeripheral* fake_peripheral = GetFakePeripheral(peripheral_address);
if (fake_peripheral == nullptr) {
std::move(callback).Run(base::nullopt);
return;
}
std::move(callback).Run(fake_peripheral->AddFakeService(service_uuid));
}
void FakeCentral::AddFakeCharacteristic(
const device::BluetoothUUID& characteristic_uuid,
mojom::CharacteristicPropertiesPtr properties,
const std::string& service_id,
const std::string& peripheral_address,
AddFakeCharacteristicCallback callback) {
FakeRemoteGattService* fake_remote_gatt_service =
GetFakeRemoteGattService(peripheral_address, service_id);
if (fake_remote_gatt_service == nullptr) {
std::move(callback).Run(base::nullopt);
return;
}
std::move(callback).Run(fake_remote_gatt_service->AddFakeCharacteristic(
characteristic_uuid, std::move(properties)));
}
void FakeCentral::RemoveFakeCharacteristic(
const std::string& identifier,
const std::string& service_id,
const std::string& peripheral_address,
RemoveFakeCharacteristicCallback callback) {
FakeRemoteGattService* fake_remote_gatt_service =
GetFakeRemoteGattService(peripheral_address, service_id);
if (fake_remote_gatt_service == nullptr) {
std::move(callback).Run(false);
return;
}
std::move(callback).Run(
fake_remote_gatt_service->RemoveFakeCharacteristic(identifier));
}
void FakeCentral::AddFakeDescriptor(
const device::BluetoothUUID& descriptor_uuid,
const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
AddFakeDescriptorCallback callback) {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
std::move(callback).Run(base::nullopt);
}
std::move(callback).Run(
fake_remote_gatt_characteristic->AddFakeDescriptor(descriptor_uuid));
}
void FakeCentral::SetNextReadCharacteristicResponse(
uint16_t gatt_code,
const base::Optional<std::vector<uint8_t>>& value,
const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
SetNextReadCharacteristicResponseCallback callback) {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
std::move(callback).Run(false);
}
fake_remote_gatt_characteristic->SetNextReadResponse(gatt_code, value);
std::move(callback).Run(true);
}
void FakeCentral::SetNextWriteCharacteristicResponse(
uint16_t gatt_code,
const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
SetNextWriteCharacteristicResponseCallback callback) {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
std::move(callback).Run(false);
}
fake_remote_gatt_characteristic->SetNextWriteResponse(gatt_code);
std::move(callback).Run(true);
}
void FakeCentral::SetNextSubscribeToNotificationsResponse(
uint16_t gatt_code,
const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
SetNextSubscribeToNotificationsResponseCallback callback) {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
std::move(callback).Run(false);
}
fake_remote_gatt_characteristic->SetNextSubscribeToNotificationsResponse(
gatt_code);
std::move(callback).Run(true);
}
void FakeCentral::GetLastWrittenValue(const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
GetLastWrittenValueCallback callback) {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
std::move(callback).Run(false, base::nullopt);
}
std::move(callback).Run(
true, fake_remote_gatt_characteristic->last_written_value());
}
void FakeCentral::SetNextReadDescriptorResponse(
uint16_t gatt_code,
const base::Optional<std::vector<uint8_t>>& value,
const std::string& descriptor_id,
const std::string& characteristic_id,
const std::string& service_id,
const std::string& peripheral_address,
SetNextReadDescriptorResponseCallback callback) {
FakeRemoteGattDescriptor* fake_remote_gatt_descriptor =
GetFakeRemoteGattDescriptor(peripheral_address, service_id,
characteristic_id, descriptor_id);
if (fake_remote_gatt_descriptor == nullptr) {
std::move(callback).Run(false);
}
fake_remote_gatt_descriptor->SetNextReadResponse(gatt_code, value);
std::move(callback).Run(true);
}
std::string FakeCentral::GetAddress() const {
NOTREACHED();
return std::string();
}
std::string FakeCentral::GetName() const {
NOTREACHED();
return std::string();
}
void FakeCentral::SetName(const std::string& name,
const base::Closure& callback,
const ErrorCallback& error_callback) {
NOTREACHED();
}
bool FakeCentral::IsInitialized() const {
return true;
}
bool FakeCentral::IsPresent() const {
switch (state_) {
case mojom::CentralState::ABSENT:
return false;
case mojom::CentralState::POWERED_OFF:
case mojom::CentralState::POWERED_ON:
return true;
}
NOTREACHED();
return false;
}
bool FakeCentral::IsPowered() const {
switch (state_) {
case mojom::CentralState::POWERED_OFF:
return false;
case mojom::CentralState::POWERED_ON:
return true;
case mojom::CentralState::ABSENT:
// Clients shouldn't call IsPowered() when the adapter is not present.
NOTREACHED();
return false;
}
NOTREACHED();
return false;
}
void FakeCentral::SetPowered(bool powered,
const base::Closure& callback,
const ErrorCallback& error_callback) {
NOTREACHED();
}
bool FakeCentral::IsDiscoverable() const {
NOTREACHED();
return false;
}
void FakeCentral::SetDiscoverable(bool discoverable,
const base::Closure& callback,
const ErrorCallback& error_callback) {
NOTREACHED();
}
bool FakeCentral::IsDiscovering() const {
NOTREACHED();
return false;
}
FakeCentral::UUIDList FakeCentral::GetUUIDs() const {
NOTREACHED();
return UUIDList();
}
void FakeCentral::CreateRfcommService(
const device::BluetoothUUID& uuid,
const ServiceOptions& options,
const CreateServiceCallback& callback,
const CreateServiceErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::CreateL2capService(
const device::BluetoothUUID& uuid,
const ServiceOptions& options,
const CreateServiceCallback& callback,
const CreateServiceErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::RegisterAdvertisement(
std::unique_ptr<device::BluetoothAdvertisement::Data> advertisement_data,
const CreateAdvertisementCallback& callback,
const AdvertisementErrorCallback& error_callback) {
NOTREACHED();
}
#if defined(OS_CHROMEOS) || defined(OS_LINUX)
void FakeCentral::SetAdvertisingInterval(
const base::TimeDelta& min,
const base::TimeDelta& max,
const base::Closure& callback,
const AdvertisementErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::ResetAdvertising(
const base::Closure& callback,
const AdvertisementErrorCallback& error_callback) {
NOTREACHED();
}
#endif
device::BluetoothLocalGattService* FakeCentral::GetGattService(
const std::string& identifier) const {
NOTREACHED();
return nullptr;
}
void FakeCentral::AddDiscoverySession(
device::BluetoothDiscoveryFilter* discovery_filter,
const base::Closure& callback,
const DiscoverySessionErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::RemoveDiscoverySession(
device::BluetoothDiscoveryFilter* discovery_filter,
const base::Closure& callback,
const DiscoverySessionErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::SetDiscoveryFilter(
std::unique_ptr<device::BluetoothDiscoveryFilter> discovery_filter,
const base::Closure& callback,
const DiscoverySessionErrorCallback& error_callback) {
NOTREACHED();
}
void FakeCentral::RemovePairingDelegateInternal(
device::BluetoothDevice::PairingDelegate* pairing_delegate) {
NOTREACHED();
}
FakeCentral::~FakeCentral() = default;
FakePeripheral* FakeCentral::GetFakePeripheral(
const std::string& peripheral_address) const {
auto device_iter = devices_.find(peripheral_address);
if (device_iter == devices_.end()) {
return nullptr;
}
// static_cast is safe because the parent class's devices_ is only
// populated via this FakeCentral, and only with FakePeripherals.
return static_cast<FakePeripheral*>(device_iter->second.get());
}
FakeRemoteGattService* FakeCentral::GetFakeRemoteGattService(
const std::string& peripheral_address,
const std::string& service_id) const {
FakePeripheral* fake_peripheral = GetFakePeripheral(peripheral_address);
if (fake_peripheral == nullptr) {
return nullptr;
}
// static_cast is safe because FakePeripheral is only populated with
// FakeRemoteGattServices.
return static_cast<FakeRemoteGattService*>(
fake_peripheral->GetGattService(service_id));
}
FakeRemoteGattCharacteristic* FakeCentral::GetFakeRemoteGattCharacteristic(
const std::string& peripheral_address,
const std::string& service_id,
const std::string& characteristic_id) const {
FakeRemoteGattService* fake_remote_gatt_service =
GetFakeRemoteGattService(peripheral_address, service_id);
if (fake_remote_gatt_service == nullptr) {
return nullptr;
}
// static_cast is safe because FakeRemoteGattService is only populated with
// FakeRemoteGattCharacteristics.
return static_cast<FakeRemoteGattCharacteristic*>(
fake_remote_gatt_service->GetCharacteristic(characteristic_id));
}
FakeRemoteGattDescriptor* FakeCentral::GetFakeRemoteGattDescriptor(
const std::string& peripheral_address,
const std::string& service_id,
const std::string& characteristic_id,
const std::string& descriptor_id) const {
FakeRemoteGattCharacteristic* fake_remote_gatt_characteristic =
GetFakeRemoteGattCharacteristic(peripheral_address, service_id,
characteristic_id);
if (fake_remote_gatt_characteristic == nullptr) {
return nullptr;
}
// static_cast is safe because FakeRemoteGattCharacteristic is only populated
// with FakeRemoteGattDescriptors.
return static_cast<FakeRemoteGattDescriptor*>(
fake_remote_gatt_characteristic->GetDescriptor(descriptor_id));
}
} // namespace bluetooth