9#include "bluez/bluez_data_p.h"
11#include <QtCore/QLoggingCategory>
12#include <QtCore/QSocketNotifier>
21 QBluetoothServiceInfo::Protocol socketType)
29 QBluetoothSocket *socket =
new QBluetoothSocket(rawSocketPrivate, socketType);
34 QBluetoothServer *parent)
35 : securityFlags(QBluetooth::Security::Authorization),
39 if (sType == QBluetoothServiceInfo::RfcommProtocol)
40 socket = createSocketForServer(QBluetoothServiceInfo::RfcommProtocol);
42 socket = createSocketForServer(QBluetoothServiceInfo::L2capProtocol);
47 delete socketNotifier;
55 socketNotifier->setEnabled(
false);
57 emit q_ptr->newConnection();
61 QBluetooth::SecurityFlags requestedSecLevel,
int *errnoCode)
63 if (requestedSecLevel == QBluetooth::SecurityFlags(QBluetooth::Security::NoSecurity)) {
64 qCWarning(QT_BT_BLUEZ) <<
"Cannot set NoSecurity on server socket";
68 struct bt_security security;
69 memset(&security, 0,
sizeof(security));
80 &security,
sizeof(security)) != 0) {
88 struct bt_security security;
89 memset(&security, 0,
sizeof(security));
90 socklen_t length =
sizeof(security);
93 &security, &length) != 0) {
94 qCWarning(QT_BT_BLUEZ) <<
"Failed to get security flags" << qt_error_string(errno);
98 switch (security.level) {
106 qCWarning(QT_BT_BLUEZ) <<
"Unknown server socket security level" << security.level;
111void QBluetoothServer::close()
113 Q_D(QBluetoothServer);
115 delete d->socketNotifier;
116 d->socketNotifier =
nullptr;
121bool QBluetoothServer::listen(
const QBluetoothAddress &address, quint16 port)
123 Q_D(QBluetoothServer);
125 if (d->socket->state() == QBluetoothSocket::SocketState::ListeningState) {
126 qCWarning(QT_BT_BLUEZ) <<
"Socket already in listen mode, close server first";
130 QBluetoothLocalDevice device(address);
131 if (!device.isValid()) {
132 qCWarning(QT_BT_BLUEZ) <<
"Device does not support Bluetooth or"
133 << address.toString() <<
"is not a valid local adapter";
134 d->m_lastError = QBluetoothServer::UnknownError;
135 emit errorOccurred(d->m_lastError);
139 QBluetoothLocalDevice::HostMode hostMode = device.hostMode();
140 if (hostMode == QBluetoothLocalDevice::HostPoweredOff) {
141 d->m_lastError = QBluetoothServer::PoweredOffError;
142 emit errorOccurred(d->m_lastError);
143 qCWarning(QT_BT_BLUEZ) <<
"Bluetooth device is powered off";
147 int sock = d->socket->socketDescriptor();
150
151
152
153
154
157 if (serverType() == QBluetoothServiceInfo::RfcommProtocol)
158 d->socket = QBluetoothServerPrivate::createSocketForServer(QBluetoothServiceInfo::RfcommProtocol);
160 d->socket = QBluetoothServerPrivate::createSocketForServer(QBluetoothServiceInfo::L2capProtocol);
162 sock = d->socket->socketDescriptor();
164 d->m_lastError = InputOutputError;
165 emit errorOccurred(d->m_lastError);
170 if (d->serverType == QBluetoothServiceInfo::RfcommProtocol) {
173 addr.rc_family = AF_BLUETOOTH;
174 addr.rc_channel = port;
176 if (!address.isNull())
177 convertAddress(address.toUInt64(), addr.rc_bdaddr.b);
179 convertAddress(device.address().toUInt64(), addr.rc_bdaddr.b);
181 if (::bind(sock,
reinterpret_cast<sockaddr *>(&addr),
sizeof(sockaddr_rc)) < 0) {
182 if (errno == EADDRINUSE)
183 d->m_lastError = ServiceAlreadyRegisteredError;
185 d->m_lastError = InputOutputError;
186 emit errorOccurred(d->m_lastError);
192 memset(&addr, 0,
sizeof(sockaddr_l2));
193 addr.l2_family = AF_BLUETOOTH;
196 if (!address.isNull())
197 convertAddress(address.toUInt64(), addr.l2_bdaddr.b);
199 convertAddress(Q_UINT64_C(0), addr.l2_bdaddr.b);
201 if (::bind(sock,
reinterpret_cast<sockaddr *>(&addr),
sizeof(sockaddr_l2)) < 0) {
202 d->m_lastError = InputOutputError;
203 emit errorOccurred(d->m_lastError);
208 d->setSocketSecurityLevel(d->securityFlags,
nullptr);
210 if (::listen(sock, d->maxPendingConnections) < 0) {
211 d->m_lastError = InputOutputError;
212 emit errorOccurred(d->m_lastError);
216 d->socket->setSocketState(QBluetoothSocket::SocketState::ListeningState);
218 if (!d->socketNotifier) {
219 d->socketNotifier =
new QSocketNotifier(d->socket->socketDescriptor(),
220 QSocketNotifier::Read);
221 connect(d->socketNotifier, &QSocketNotifier::activated,
223 d->_q_newConnection();
230void QBluetoothServer::setMaxPendingConnections(
int numConnections)
232 Q_D(QBluetoothServer);
234 if (d->socket->state() == QBluetoothSocket::SocketState::UnconnectedState)
235 d->maxPendingConnections = numConnections;
238bool QBluetoothServer::hasPendingConnections()
const
240 Q_D(
const QBluetoothServer);
242 if (!d || !d->socketNotifier)
246 return !d->socketNotifier->isEnabled();
249QBluetoothSocket *QBluetoothServer::nextPendingConnection()
251 Q_D(QBluetoothServer);
253 if (!hasPendingConnections())
257 if (d->serverType == QBluetoothServiceInfo::RfcommProtocol) {
259 socklen_t length =
sizeof(sockaddr_rc);
260 pending = ::accept(d->socket->socketDescriptor(),
261 reinterpret_cast<sockaddr *>(&addr), &length);
264 socklen_t length =
sizeof(sockaddr_l2);
265 pending = ::accept(d->socket->socketDescriptor(),
266 reinterpret_cast<sockaddr *>(&addr), &length);
270 QBluetoothSocket *newSocket = QBluetoothServerPrivate::createSocketForServer();
271 if (d->serverType == QBluetoothServiceInfo::RfcommProtocol)
272 newSocket->setSocketDescriptor(pending, QBluetoothServiceInfo::RfcommProtocol);
274 newSocket->setSocketDescriptor(pending, QBluetoothServiceInfo::L2capProtocol);
276 d->socketNotifier->setEnabled(
true);
280 d->socketNotifier->setEnabled(
true);
286QBluetoothAddress QBluetoothServer::serverAddress()
const
288 Q_D(
const QBluetoothServer);
290 return d->socket->localAddress();
293quint16 QBluetoothServer::serverPort()
const
295 Q_D(
const QBluetoothServer);
297 return d->socket->localPort();
300void QBluetoothServer::setSecurityFlags(QBluetooth::SecurityFlags security)
302 Q_D(QBluetoothServer);
304 if (d->socket->state() == QBluetoothSocket::SocketState::UnconnectedState) {
306 d->securityFlags = security;
311 d->setSocketSecurityLevel(security, &errorCode);
313 qCWarning(QT_BT_BLUEZ) <<
"Failed to set socket option, closing socket for safety" << errorCode;
314 qCWarning(QT_BT_BLUEZ) <<
"Error: " << qt_error_string(errorCode);
315 d->m_lastError = InputOutputError;
316 emit errorOccurred(d->m_lastError);
321QBluetooth::SecurityFlags QBluetoothServer::securityFlags()
const
323 Q_D(
const QBluetoothServer);
325 if (d->socket->state() == QBluetoothSocket::SocketState::UnconnectedState)
326 return d->securityFlags;
328 return d->socketSecurityLevel();
#define BT_SECURITY_MEDIUM
~QBluetoothServerPrivate()
QBluetoothSocket * socket
QBluetoothSocketPrivateBluez()
QT_BEGIN_NAMESPACE Q_DECLARE_LOGGING_CATEGORY(lcEventDispatcher)