18#include <QtCore/qloggingcategory.h> 
   19#include <QtCore/qsharedpointer.h> 
   20#include <QtCore/qbytearray.h> 
   21#include <QtCore/qglobal.h> 
   22#include <QtCore/qstring.h> 
   23#include <QtCore/qlist.h> 
   24#include <QtCore/qcoreapplication.h> 
   25#include <QtCore/qpermissions.h> 
   39    CBUUID *
const cbUuid = cbService.UUID;
 
   41        qCDebug(QT_BT_DARWIN) << 
"invalid service, UUID is nil";
 
   50    newService->
uuid = qtUuid;
 
   90    qRegisterMetaType<QLowEnergyHandle>(
"QLowEnergyHandle");
 
   91    qRegisterMetaType<QSharedPointer<QLowEnergyServicePrivate>>();
 
   99            dispatch_sync(leQueue, ^{
 
  104            dispatch_sync(leQueue, ^{
 
  113    return centralManager || peripheralManager;
 
  127    if (peripheralManager || centralManager)
 
  132                  "Use of Bluetooth LE must be explicitly requested by the application.");
 
  137    std::unique_ptr<LECBManagerNotifier> 
notifier = std::make_unique<LECBManagerNotifier>();
 
  150        qCWarning(QT_BT_DARWIN) << 
"failed to connect to notifier's signal(s)";
 
  183    dispatch_async(leQueue, ^{
 
  198    const auto oldState = 
state;
 
  205        dispatch_async(leQueue, ^{
 
  217        qCCritical(QT_BT_DARWIN) << 
"qt LE queue is nil, " 
  218                                    "can not dispatch 'disconnect'";
 
  237    dispatch_async(leQueue, ^{
 
  247        qCWarning(QT_BT_DARWIN) << 
"can not discover service details in the current state, " 
  248                                   "QLowEnergyController::DiscoveredState is expected";
 
  253        qCWarning(QT_BT_DARWIN) << 
"unknown service: " << serviceUuid;
 
  260    ServicePrivate qtService(
serviceList.value(serviceUuid));
 
  265    dispatch_async(leQueue, ^{
 
  274    qCWarning(QT_BT_DARWIN) << 
"Connection update not implemented on your platform";
 
  297        dispatch_sync(leQueue, ^{
 
  314        dispatch_async(leQueue, ^{
 
  323        qCWarning(QT_BT_DARWIN) << 
"invalid peripheral";
 
  327    for (
auto includedService : service.includedServices())
 
  332    if (
const auto servicePrivate = [
manager addService:service]) {
 
  333        servicePrivate->setController(
this);
 
  342void QLowEnergyControllerPrivateDarwin::_q_connected()
 
  348void QLowEnergyControllerPrivateDarwin::_q_disconnected()
 
  357void QLowEnergyControllerPrivateDarwin::_q_mtuChanged(
int newValue)
 
  362void QLowEnergyControllerPrivateDarwin::_q_serviceDiscoveryFinished()
 
  384            if (!newService.data())
 
  388                qCDebug(QT_BT_DARWIN) << 
"discovered service with a duplicated UUID" 
  393            discoveredCBServices.
insert(newService->uuid, cbService);
 
  402                CBService *
const s = [toVisit objectAtIndex:
i];
 
  403                if (![visited containsObject:
s]) {
 
  404                    [visited addObject:
s];
 
  405                    if (
s.includedServices && 
s.includedServices.count)
 
  406                        [toVisitNext addObjectsFromArray:
s.includedServices];
 
  417            if (![toVisitNext 
count])
 
  421                CBService *
const s = [toVisitNext objectAtIndex:
i];
 
  424                    if (discoveredCBServices.
value(uuid) == 
s) {
 
  432                    discoveredCBServices.
insert(newService->uuid, 
s);
 
  436            toVisit.
swap(toVisitNext);
 
  437            toVisitNext.reset([[NSMutableArray alloc] 
init], RetainPolicy::noInitialRetain);
 
  440        qCDebug(QT_BT_DARWIN) << 
"no services found";
 
  462        qCDebug(QT_BT_DARWIN) << 
"unknown service uuid:" 
  469    qtService->startHandle = 
service->startHandle;
 
  470    qtService->endHandle = 
service->endHandle;
 
  471    qtService->characteristicList = 
service->characteristicList;
 
  476void QLowEnergyControllerPrivateDarwin::_q_servicesWereModified()
 
  480        qCWarning(QT_BT_DARWIN) << 
"services were modified while controller is not in Discovered/Discovering state";
 
  491void QLowEnergyControllerPrivateDarwin::_q_characteristicRead(
QLowEnergyHandle charHandle,
 
  501    if (!characteristic.isValid()) {
 
  502        qCWarning(QT_BT_DARWIN) << 
"unknown characteristic";
 
  507        updateValueOfCharacteristic(charHandle, 
value, 
false);
 
  512void QLowEnergyControllerPrivateDarwin::_q_characteristicWritten(
QLowEnergyHandle charHandle,
 
  519        qCWarning(QT_BT_DARWIN) << 
"can not find service for characteristic handle" 
  525    if (!characteristic.isValid()) {
 
  526        qCWarning(QT_BT_DARWIN) << 
"unknown characteristic";
 
  531        updateValueOfCharacteristic(charHandle, 
value, 
false);
 
  536void QLowEnergyControllerPrivateDarwin::_q_characteristicUpdated(
QLowEnergyHandle charHandle,
 
  554    if (!characteristic.isValid()) {
 
  555        qCWarning(QT_BT_DARWIN) << 
"unknown characteristic";
 
  560        updateValueOfCharacteristic(charHandle, 
value, 
false);
 
  565void QLowEnergyControllerPrivateDarwin::_q_descriptorRead(
QLowEnergyHandle dHandle,
 
  571    if (!qtDescriptor.isValid()) {
 
  572        qCWarning(QT_BT_DARWIN) << 
"unknown descriptor" << dHandle;
 
  577    updateValueOfDescriptor(qtDescriptor.characteristicHandle(), dHandle, 
value, 
false);
 
  581void QLowEnergyControllerPrivateDarwin::_q_descriptorWritten(
QLowEnergyHandle dHandle,
 
  587    if (!qtDescriptor.isValid()) {
 
  588        qCWarning(QT_BT_DARWIN) << 
"unknown descriptor" << dHandle;
 
  594    updateValueOfDescriptor(qtDescriptor.characteristicHandle(), dHandle, 
value, 
false);
 
  598void QLowEnergyControllerPrivateDarwin::_q_notificationEnabled(
QLowEnergyHandle charHandle,
 
  609               "controller has an invalid role, 'peripheral' expected");
 
  613    if (!qtChar.isValid()) {
 
  614        qCWarning(QT_BT_DARWIN) << 
"unknown characteristic" << charHandle;
 
  621        qCWarning(QT_BT_DARWIN) << 
"characteristic" << charHandle
 
  622                                << 
"does not have a client characteristic " 
  636        updateValueOfDescriptor(charHandle, qtDescriptor.handle(), 
value, 
false);
 
  641void QLowEnergyControllerPrivateDarwin::_q_LEnotSupported()
 
  651    qCDebug(QT_BT_DARWIN) << 
"QLowEnergyController error:" << errorCode << 
"in state:" << 
state;
 
  669void QLowEnergyControllerPrivateDarwin::_q_CBManagerError(
const QBluetoothUuid &serviceUuid,
 
  680        qCDebug(QT_BT_DARWIN) << 
"error reported for unknown service" 
  685void QLowEnergyControllerPrivateDarwin::_q_CBManagerError(
const QBluetoothUuid &serviceUuid,
 
  689        qCDebug(QT_BT_DARWIN) << 
"unknown service uuid:" 
  705        qCWarning(QT_BT_DARWIN) << 
"invalid role (peripheral)";
 
  710    if (newValue.
size() > 2) {
 
  715        qCWarning(QT_BT_DARWIN) << 
"client characteristic configuration descriptor" 
  716                                   "is 2 bytes, but value size is: " << newValue.
size();
 
  722        qCWarning(QT_BT_DARWIN) << 
"no service with uuid:" << 
service->uuid << 
"found";
 
  726    if (!
service->characteristicList.contains(charHandle)) {
 
  727        qCDebug(QT_BT_DARWIN) << 
"no characteristic with handle:" 
  728                              << charHandle << 
"found";
 
  738    dispatch_async(leQueue, ^{
 
  739        [
manager setNotifyValue:newValueCopy
 
  740                 forCharacteristic:charHandle
 
  741                 onService:serviceUuid];
 
  751        qCWarning(QT_BT_DARWIN) << 
"invalid role (peripheral)";
 
  756        qCWarning(QT_BT_DARWIN) << 
"no service with uuid:" 
  757                                << service->uuid << 
"found";
 
  761    if (!service->characteristicList.contains(charHandle)) {
 
  762        qCDebug(QT_BT_DARWIN) << 
"no characteristic with handle:" 
  763                              << charHandle << 
"found";
 
  773    dispatch_async(leQueue, ^{
 
  788        qCWarning(QT_BT_DARWIN) << 
"no service with uuid:" 
  789                                << service->uuid << 
" found";
 
  793    if (!service->characteristicList.contains(charHandle)) {
 
  794        qCDebug(QT_BT_DARWIN) << 
"no characteristic with handle:" 
  795                              << charHandle << 
" found";
 
  806        dispatch_async(leQueue, ^{
 
  808                charHandle:charHandle
 
  809                 onService:serviceUuid
 
  814        dispatch_async(leQueue, ^{
 
  825    if (!service.isNull()) {
 
  827        if (charIt != service->characteristicList.end()) {
 
  850        qCWarning(QT_BT_DARWIN) << 
"invalid role (peripheral)";
 
  855        qCWarning(QT_BT_DARWIN) << 
"no service with uuid:" 
  856                                << service->uuid << 
"found";
 
  862        qCWarning(QT_BT_DARWIN) << 
"no LE queue found";
 
  868    dispatch_async(leQueue, ^{
 
  870                 onService:serviceUuid];
 
  884        qCWarning(QT_BT_DARWIN) << 
"invalid role (peripheral)";
 
  892        qCWarning(QT_BT_DARWIN) << 
"no service with uuid:" 
  893                                << service->uuid << 
" found";
 
  903    dispatch_async(leQueue, ^{
 
  905                 descHandle:descriptorHandle
 
  906                 onService:serviceUuid];
 
  914    if (!service.isNull()) {
 
  916        if (charIt != service->characteristicList.end()) {
 
  943                      this, &QLowEnergyControllerPrivateDarwin::_q_connected);
 
  945                       this, &QLowEnergyControllerPrivateDarwin::_q_disconnected);
 
  947                       this, &QLowEnergyControllerPrivateDarwin::_q_serviceDiscoveryFinished);
 
  949                       this, &QLowEnergyControllerPrivateDarwin::_q_servicesWereModified);
 
  951                       this, &QLowEnergyControllerPrivateDarwin::_q_serviceDetailsDiscoveryFinished);
 
  953                       this, &QLowEnergyControllerPrivateDarwin::_q_characteristicRead);
 
  955                       this, &QLowEnergyControllerPrivateDarwin::_q_characteristicWritten);
 
  957                       this, &QLowEnergyControllerPrivateDarwin::_q_characteristicUpdated);
 
  959                       this, &QLowEnergyControllerPrivateDarwin::_q_descriptorRead);
 
  961                       this, &QLowEnergyControllerPrivateDarwin::_q_descriptorWritten);
 
  963                       this, &QLowEnergyControllerPrivateDarwin::_q_notificationEnabled);
 
  965                       this, &QLowEnergyControllerPrivateDarwin::_q_LEnotSupported);
 
  973                       &QLowEnergyControllerPrivateDarwin::_q_mtuChanged);
 
  994    [
manager setParameters:
params data:advertisingData scanResponse:scanResponseData];
 
  998    dispatch_async(leQueue, ^{
 
 1009        qCDebug(QT_BT_DARWIN) << 
"cannot stop advertising, called in state" << 
state;
 
 1016    dispatch_sync(leQueue, ^{
 
CBPeripheral * peripheral
DarwinBluetooth::LECBManagerNotifier * notifier
std::vector< ObjCStrongReference< CBMutableService > > services
#define QT_BT_MAC_AUTORELEASEPOOL
void swap(StrongReference &other) noexcept
Access Bluetooth peripherals.
@ ClientCharacteristicConfiguration
qsizetype size() const noexcept
Returns the number of bytes in this byte array.
void append(parameter_type t)
The QLowEnergyAdvertisingData class represents the data to be broadcast during Bluetooth Low Energy a...
The QLowEnergyAdvertisingParameters class represents the parameters used for Bluetooth Low Energy adv...
The QLowEnergyConnectionParameters class is used when requesting or reporting an update of the parame...
void discoverServices() override
void writeDescriptor(const QSharedPointer< QLowEnergyServicePrivate > service, const QLowEnergyHandle charHandle, const QLowEnergyHandle descriptorHandle, const QByteArray &newValue) override
void readDescriptor(const QSharedPointer< QLowEnergyServicePrivate > service, const QLowEnergyHandle charHandle, const QLowEnergyHandle descriptorHandle) override
void startAdvertising(const QLowEnergyAdvertisingParameters ¶ms, const QLowEnergyAdvertisingData &advertisingData, const QLowEnergyAdvertisingData &scanResponseData) override
void connectToDevice() override
void disconnectFromDevice() override
~QLowEnergyControllerPrivateDarwin()
void writeCharacteristic(const QSharedPointer< QLowEnergyServicePrivate > service, const QLowEnergyHandle charHandle, const QByteArray &newValue, QLowEnergyService::WriteMode mode) override
void discoverServiceDetails(const QBluetoothUuid &serviceUuid, QLowEnergyService::DiscoveryMode mode) override
QLowEnergyControllerPrivateDarwin()
friend class QLowEnergyService
QLowEnergyService * addServiceHelper(const QLowEnergyServiceData &service) override
void addToGenericAttributeList(const QLowEnergyServiceData &service, QLowEnergyHandle startHandle) override
void stopAdvertising() override
void requestConnectionUpdate(const QLowEnergyConnectionParameters ¶ms) override
void readCharacteristic(const QSharedPointer< QLowEnergyServicePrivate > service, const QLowEnergyHandle charHandle) override
QLowEnergyCharacteristic characteristicForHandle(QLowEnergyHandle handle)
Returns a valid characteristic if the given handle is the handle of the characteristic itself or one ...
QSharedPointer< QLowEnergyServicePrivate > serviceForHandle(QLowEnergyHandle handle)
void invalidateServices()
QLowEnergyDescriptor descriptorForHandle(QLowEnergyHandle handle)
Returns a valid descriptor if handle belongs to a descriptor; otherwise an invalid one.
ServiceDataMap localServices
ServiceDataMap serviceList
void setError(QLowEnergyController::Error newError)
QLowEnergyController::Role role
QBluetoothUuid deviceUuid
QLowEnergyController * q_ptr
QLowEnergyController::ControllerState state
void setState(QLowEnergyController::ControllerState newState)
ControllerState
Indicates the state of the controller object.
void connected()
This signal is emitted when the controller successfully connects to the remote Low Energy device (if ...
void rssiRead(qint16 rssi)
This signal is emitted after successful read of RSSI (received signal strength indicator) for a conne...
Error
Indicates all possible error conditions found during the controller's existence.
@ UnknownRemoteDeviceError
@ MissingPermissionsError
void disconnected()
This signal is emitted when the controller disconnects from the remote Low Energy device or vice vers...
void discoverServices()
Initiates the service discovery process.
void discoveryFinished()
This signal is emitted when the running service discovery finishes.
void mtuChanged(int mtu)
This signal is emitted as a result of a successful MTU change.
bool isValid() const
Returns true if the QLowEnergyDescriptor object is valid, otherwise returns false.
The QLowEnergyServiceData class is used to set up GATT service data. \inmodule QtBluetooth.
void setController(QLowEnergyControllerPrivate *control)
QLowEnergyService::ServiceTypes type
DiscoveryMode
This enum lists service discovery modes.
ServiceError
This enum describes all possible error conditions during the service's existence.
@ RemoteServiceDiscovered
@ RemoteServiceDiscovering
WriteMode
This enum describes the mode to be used when writing a characteristic value.
iterator insert(const Key &key, const T &value)
T value(const Key &key, const T &defaultValue=T()) const
static QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
\threadsafe
static bool disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *member)
\threadsafe
bool isNull() const noexcept
Returns true if this is the null UUID {00000000-0000-0000-0000-000000000000}; otherwise returns false...
QSet< QString >::iterator it
QBluetoothUuid qt_uuid(NSUUID *nsUuid)
dispatch_queue_t qt_LE_queue()
Combined button and popup list for selecting options.
ServicePrivate qt_createLEService(QLowEnergyControllerPrivateDarwin *controller, CBService *cbService, bool included)
QSharedPointer< QLowEnergyServicePrivate > ServicePrivate
UUIDList qt_servicesUuids(NSArray *services)
Q_CORE_EXPORT QtJniTypes::Service service()
EGLOutputLayerEXT EGLint EGLAttrib value
[5]
#define qCCritical(category,...)
#define qCWarning(category,...)
#define qCDebug(category,...)
void registerQLowEnergyControllerMetaType()
#define Q_ARG(Type, data)
GLenum GLenum GLsizei count
GLenum GLenum GLsizei const GLuint GLboolean enabled
GLint GLsizei GLsizei GLenum GLenum GLsizei void * data
#define Q_ASSERT_X(cond, x, msg)
gzip write("uncompressed data")
QNetworkAccessManager manager
QHash< QLowEnergyHandle, DescData > descriptorList