diff options
Diffstat (limited to 'src/bluetooth')
-rw-r--r-- | src/bluetooth/qbluetoothservicediscoveryagent_winrt.cpp | 11 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothsocket.cpp | 7 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothsocket_winrt.cpp | 64 | ||||
-rw-r--r-- | src/bluetooth/qbluetoothsocket_winrt_p.h | 15 |
4 files changed, 80 insertions, 17 deletions
diff --git a/src/bluetooth/qbluetoothservicediscoveryagent_winrt.cpp b/src/bluetooth/qbluetoothservicediscoveryagent_winrt.cpp index 9f82a202..3b99c1c4 100644 --- a/src/bluetooth/qbluetoothservicediscoveryagent_winrt.cpp +++ b/src/bluetooth/qbluetoothservicediscoveryagent_winrt.cpp @@ -52,6 +52,7 @@ #include <windows.devices.enumeration.h> #include <windows.devices.bluetooth.h> #include <windows.foundation.collections.h> +#include <windows.networking.h> #include <windows.storage.streams.h> #include <wrl.h> @@ -208,6 +209,14 @@ void QWinRTBluetoothServiceDiscoveryWorker::processServiceSearchResult(quint64 a hr = service->get_ConnectionServiceName(name.GetAddressOf()); Q_ASSERT_SUCCEEDED(hr); const QString serviceName = QString::fromWCharArray(WindowsGetStringRawBuffer(name.Get(), nullptr)); + ComPtr<ABI::Windows::Networking::IHostName> host; + hr = service->get_ConnectionHostName(host.GetAddressOf()); + Q_ASSERT_SUCCEEDED(hr); + HString hostName; + hr = host->get_RawName(hostName.GetAddressOf()); + Q_ASSERT_SUCCEEDED(hr); + const QString qHostName = QString::fromWCharArray(WindowsGetStringRawBuffer(hostName.Get(), + nullptr)); ComPtr<IRfcommServiceId> id; hr = service->get_ServiceId(&id); Q_ASSERT_SUCCEEDED(hr); @@ -217,6 +226,8 @@ void QWinRTBluetoothServiceDiscoveryWorker::processServiceSearchResult(quint64 a Q_ASSERT_SUCCEEDED(hr); QBluetoothServiceInfo info; + info.setAttribute(0xBEEF, QVariant(qHostName)); + info.setAttribute(0xBEF0, QVariant(serviceName)); info.setServiceName(serviceName); info.setServiceUuid(uuid); ComPtr<IAsyncOperation<IMapView<UINT32, IBuffer *> *>> op; diff --git a/src/bluetooth/qbluetoothsocket.cpp b/src/bluetooth/qbluetoothsocket.cpp index a18b8ed4..db7c8be4 100644 --- a/src/bluetooth/qbluetoothsocket.cpp +++ b/src/bluetooth/qbluetoothsocket.cpp @@ -640,6 +640,13 @@ void QBluetoothSocket::serviceDiscovered(const QBluetoothServiceInfo &service) connectToService(service, d->openMode); d->discoveryAgent->deleteLater(); d->discoveryAgent = nullptr; +#ifdef QT_WINRT_BLUETOOTH + } else if (!service.attribute(0xBEEF).isNull() + && !service.attribute(0xBEF0).isNull()) { + connectToService(service, d->openMode); + d->discoveryAgent->deleteLater(); + d->discoveryAgent = nullptr; +#endif } else { qCDebug(QT_BT) << "Could not find port/psm for potential remote service"; } diff --git a/src/bluetooth/qbluetoothsocket_winrt.cpp b/src/bluetooth/qbluetoothsocket_winrt.cpp index a4af8f72..72d72040 100644 --- a/src/bluetooth/qbluetoothsocket_winrt.cpp +++ b/src/bluetooth/qbluetoothsocket_winrt.cpp @@ -359,10 +359,11 @@ bool QBluetoothSocketPrivateWinRT::ensureNativeSocket(QBluetoothServiceInfo::Pro return true; } -void QBluetoothSocketPrivateWinRT::connectToServiceHelper(const QBluetoothAddress &address, quint16 port, QIODevice::OpenMode openMode) +void QBluetoothSocketPrivateWinRT::connectToService(Microsoft::WRL::ComPtr<IHostName> hostName, + const QString &serviceName, + QIODevice::OpenMode openMode) { Q_Q(QBluetoothSocket); - Q_UNUSED(openMode); if (socket == -1 && !ensureNativeSocket(socketType)) { errorString = QBluetoothSocket::tr("Unknown socket error"); @@ -370,20 +371,9 @@ void QBluetoothSocketPrivateWinRT::connectToServiceHelper(const QBluetoothAddres return; } - const QString addressString = address.toString(); - HStringReference hostNameRef(reinterpret_cast<LPCWSTR>(addressString.utf16())); - ComPtr<IHostNameFactory> hostNameFactory; - HRESULT hr = GetActivationFactory(HString::MakeReference(RuntimeClass_Windows_Networking_HostName).Get(), - &hostNameFactory); - Q_ASSERT_SUCCEEDED(hr); - ComPtr<IHostName> remoteHost; - hr = hostNameFactory->CreateHostName(hostNameRef.Get(), &remoteHost); - RETURN_VOID_IF_FAILED("QBluetoothSocketPrivateWinRT::connectToService: Could not create hostname."); - - const QString portString = QString::number(port); - HStringReference portReference(reinterpret_cast<LPCWSTR>(portString.utf16())); + HStringReference serviceNameReference(reinterpret_cast<LPCWSTR>(serviceName.utf16())); - hr = m_socketObject->ConnectAsync(remoteHost.Get(), portReference.Get(), &m_connectOp); + HRESULT hr = m_socketObject->ConnectAsync(hostName.Get(), serviceNameReference.Get(), &m_connectOp); if (hr == E_ACCESSDENIED) { qErrnoWarning(hr, "QBluetoothSocketPrivateWinRT::connectToService: Unable to connect to bluetooth socket." "Please check your manifest capabilities."); @@ -404,6 +394,29 @@ void QBluetoothSocketPrivateWinRT::connectToServiceHelper(const QBluetoothAddres Q_ASSERT_SUCCEEDED(hr); } +void QBluetoothSocketPrivateWinRT::connectToServiceHelper(const QBluetoothAddress &address, quint16 port, QIODevice::OpenMode openMode) +{ + Q_Q(QBluetoothSocket); + + if (socket == -1 && !ensureNativeSocket(socketType)) { + errorString = QBluetoothSocket::tr("Unknown socket error"); + q->setSocketError(QBluetoothSocket::UnknownSocketError); + return; + } + + const QString addressString = address.toString(); + HStringReference hostNameRef(reinterpret_cast<LPCWSTR>(addressString.utf16())); + ComPtr<IHostNameFactory> hostNameFactory; + HRESULT hr = GetActivationFactory(HString::MakeReference(RuntimeClass_Windows_Networking_HostName).Get(), + &hostNameFactory); + Q_ASSERT_SUCCEEDED(hr); + ComPtr<IHostName> remoteHost; + hr = hostNameFactory->CreateHostName(hostNameRef.Get(), &remoteHost); + RETURN_VOID_IF_FAILED("QBluetoothSocketPrivateWinRT::connectToService: Could not create hostname."); + const QString portString = QString::number(port); + connectToService(remoteHost, portString, openMode); +} + void QBluetoothSocketPrivateWinRT::connectToService( const QBluetoothServiceInfo &service, QIODevice::OpenMode openMode) { @@ -425,6 +438,8 @@ void QBluetoothSocketPrivateWinRT::connectToService( return; } + const QString connectionHostName = service.attribute(0xBEEF).toString(); + const QString connectionServiceName = service.attribute(0xBEF0).toString(); if (service.protocolServiceMultiplexer() > 0) { Q_ASSERT(service.socketProtocol() == QBluetoothServiceInfo::L2capProtocol); @@ -434,7 +449,22 @@ void QBluetoothSocketPrivateWinRT::connectToService( return; } connectToServiceHelper(service.device().address(), service.protocolServiceMultiplexer(), openMode); - } else if (service.serverChannel() > 0) { + } else if (!connectionHostName.isEmpty() && !connectionServiceName.isEmpty()) { + Q_ASSERT(service.socketProtocol() == QBluetoothServiceInfo::RfcommProtocol); + if (!ensureNativeSocket(QBluetoothServiceInfo::RfcommProtocol)) { + errorString = QBluetoothSocket::tr("Unknown socket error"); + q->setSocketError(QBluetoothSocket::UnknownSocketError); + return; + } + HStringReference hostNameRef(reinterpret_cast<LPCWSTR>(connectionHostName.utf16())); + ComPtr<IHostNameFactory> hostNameFactory; + HRESULT hr = GetActivationFactory(HString::MakeReference(RuntimeClass_Windows_Networking_HostName).Get(), + &hostNameFactory); + Q_ASSERT_SUCCEEDED(hr); + ComPtr<IHostName> remoteHost; + hr = hostNameFactory->CreateHostName(hostNameRef.Get(), &remoteHost); + connectToService(remoteHost, connectionServiceName, openMode); + } else if (service.serverChannel() > 0) { Q_ASSERT(service.socketProtocol() == QBluetoothServiceInfo::RfcommProtocol); if (!ensureNativeSocket(QBluetoothServiceInfo::RfcommProtocol)) { @@ -443,7 +473,7 @@ void QBluetoothSocketPrivateWinRT::connectToService( return; } connectToServiceHelper(service.device().address(), service.serverChannel(), openMode); - } else { + } else { // try doing service discovery to see if we can find the socket if (service.serviceUuid().isNull() && !service.serviceClassUuids().contains(QBluetoothUuid::SerialPort)) { diff --git a/src/bluetooth/qbluetoothsocket_winrt_p.h b/src/bluetooth/qbluetoothsocket_winrt_p.h index 40e87f01..de8b7d67 100644 --- a/src/bluetooth/qbluetoothsocket_winrt_p.h +++ b/src/bluetooth/qbluetoothsocket_winrt_p.h @@ -57,6 +57,19 @@ QT_FORWARD_DECLARE_CLASS(SocketWorker) +namespace ABI { + namespace Windows { + namespace Networking { + struct IHostName; + } + } +} + +namespace Microsoft { + namespace WRL { + template <typename T> class ComPtr; + } +} QT_BEGIN_NAMESPACE class QBluetoothSocketPrivateWinRT final: public QBluetoothSocketBasePrivate @@ -125,6 +138,8 @@ private slots: void handleError(QBluetoothSocket::SocketError error); private: + void connectToService(Microsoft::WRL::ComPtr<ABI::Windows::Networking::IHostName> hostName, + const QString &serviceName, QIODevice::OpenMode openMode); HRESULT handleConnectOpFinished(ABI::Windows::Foundation::IAsyncAction *action, ABI::Windows::Foundation::AsyncStatus status); |