From a61247723a7b8b371a7328d1d7ec5ca4a5ff3d84 Mon Sep 17 00:00:00 2001 From: Lorn Potter Date: Fri, 7 Nov 2014 14:05:41 +1000 Subject: Make QtBearer networkmanager backend respond to wired cabling changes Cabling changes can be detected right away, so we should act on that and change the configuration state. Change-Id: Ifa9709077215567001e11ab655208a2c1b090073 Reviewed-by: Alex Blasche --- .../networkmanager/qnetworkmanagerengine.cpp | 128 +++++++++++++++------ .../bearer/networkmanager/qnetworkmanagerengine.h | 4 + .../networkmanager/qnetworkmanagerservice.cpp | 30 +++-- .../bearer/networkmanager/qnetworkmanagerservice.h | 4 +- 4 files changed, 124 insertions(+), 42 deletions(-) (limited to 'src/plugins/bearer/networkmanager') diff --git a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp index 9adadb8f4f..6be682878d 100644 --- a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp +++ b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.cpp @@ -98,6 +98,9 @@ QNetworkManagerEngine::~QNetworkManagerEngine() qDeleteAll(ofonoContextManagers); ofonoContextManagers.clear(); + + qDeleteAll(wiredDevices); + wiredDevices.clear(); } void QNetworkManagerEngine::initialize() @@ -111,13 +114,6 @@ void QNetworkManagerEngine::initialize() ofonoContextManagers.insert(modem, ofonoContextManager); } } - // Get current list of access points. - foreach (const QDBusObjectPath &devicePath, managerInterface->getDevices()) { - locker.unlock(); - deviceAdded(devicePath); //add all accesspoints - locker.relock(); - } - // Get active connections. foreach (const QDBusObjectPath &acPath, managerInterface->activeConnections()) { @@ -128,13 +124,20 @@ void QNetworkManagerEngine::initialize() this, SLOT(activeConnectionPropertiesChanged(QMap))); activeConnection->setConnections(); - QList devices = activeConnection->devices(); + QStringList devices = activeConnection->devices(); if (!devices.isEmpty()) { - QNetworkManagerInterfaceDevice device(devices.at(0).path(),this); + QNetworkManagerInterfaceDevice device(devices.at(0),this); connectionInterfaces.insert(activeConnection->connection().path(),device.networkInterface()); } } + // Get current list of access points. + foreach (const QDBusObjectPath &devicePath, managerInterface->getDevices()) { + locker.unlock(); + deviceAdded(devicePath); //add all accesspoints + locker.relock(); + } + // Get connections. foreach (const QDBusObjectPath &settingsPath, systemSettings->listConnections()) { locker.unlock(); @@ -338,9 +341,9 @@ void QNetworkManagerEngine::activeConnectionPropertiesChanged(const QMapmutex.lock(); if (properties.value("State").toUInt() == NM_ACTIVE_CONNECTION_STATE_ACTIVATED) { - QList devices = activeConnection->devices(); + QStringList devices = activeConnection->devices(); if (!devices.isEmpty()) { - QNetworkManagerInterfaceDevice device(devices.at(0).path(),this); + QNetworkManagerInterfaceDevice device(devices.at(0),this); connectionInterfaces.insert(id,device.networkInterface()); } @@ -405,6 +408,13 @@ void QNetworkManagerEngine::deviceAdded(const QDBusObjectPath &path) wirelessDevices.insert(path.path(), wirelessDevice); } + + if (iDevice->deviceType() == DEVICE_TYPE_ETHERNET) { + QNetworkManagerInterfaceDeviceWired *wiredDevice = + new QNetworkManagerInterfaceDeviceWired(iDevice->connectionInterface()->path(),this); + connect(wiredDevice,SIGNAL(carrierChanged(bool)),this,SLOT(wiredCarrierChanged(bool))); + wiredDevices.insert(iDevice->connectionInterface()->path(), wiredDevice); + } } void QNetworkManagerEngine::deviceRemoved(const QDBusObjectPath &path) @@ -421,6 +431,41 @@ void QNetworkManagerEngine::deviceRemoved(const QDBusObjectPath &path) delete wirelessDevices.take(path.path()); locker.relock(); } + if (wiredDevices.contains(path.path())) { + locker.unlock(); + delete wiredDevices.take(path.path()); + locker.relock(); + } +} + +void QNetworkManagerEngine::wiredCarrierChanged(bool carrier) +{ + QNetworkManagerInterfaceDeviceWired *deviceWired = qobject_cast(sender()); + if (!deviceWired) + return; + QMutexLocker locker(&mutex); + foreach (const QDBusObjectPath &settingsPath, systemSettings->listConnections()) { + for (int i = 0; i < connections.count(); ++i) { + QNetworkManagerSettingsConnection *connection = connections.at(i); + if (connection->getType() == DEVICE_TYPE_ETHERNET + && settingsPath.path() == connection->connectionInterface()->path()) { + QNetworkConfigurationPrivatePointer ptr = + accessPointConfigurations.value(settingsPath.path()); + + if (ptr) { + ptr->mutex.lock(); + if (carrier) + ptr->state |= QNetworkConfiguration::Discovered; + else + ptr->state = QNetworkConfiguration::Defined; + ptr->mutex.unlock(); + locker.unlock(); + emit configurationChanged(ptr); + return; + } + } + } + } } void QNetworkManagerEngine::newConnection(const QDBusObjectPath &path, @@ -437,32 +482,37 @@ void QNetworkManagerEngine::newConnection(const QDBusObjectPath &path, QNetworkManagerSettingsConnection *connection = new QNetworkManagerSettingsConnection(settings->connectionInterface()->service(), path.path(),this); - QString apPath; - for (int i = 0; i < accessPoints.count(); ++i) { - if (connection->getSsid() == accessPoints.at(i)->ssid()) { - // remove the corresponding accesspoint from configurations - apPath = accessPoints.at(i)->connectionInterface()->path(); - - QNetworkConfigurationPrivatePointer ptr - = accessPointConfigurations.take(apPath); - if (ptr) { - locker.unlock(); - emit configurationRemoved(ptr); - locker.relock(); - } - } + const QString settingsPath = connection->connectionInterface()->path(); + if (accessPointConfigurations.contains(settingsPath)) { + return; } + connections.append(connection); connect(connection,SIGNAL(removed(QString)),this,SLOT(removeConnection(QString))); connect(connection,SIGNAL(updated()),this,SLOT(updateConnection())); connection->setConnections(); - const QString settingsPath = connection->connectionInterface()->path(); + NMDeviceType deviceType = connection->getType(); - if (connection->getType() == DEVICE_TYPE_WIFI - && !configuredAccessPoints.contains(settingsPath)) - configuredAccessPoints.insert(apPath,settingsPath); + if (deviceType == DEVICE_TYPE_WIFI) { + QString apPath; + for (int i = 0; i < accessPoints.count(); ++i) { + if (connection->getSsid() == accessPoints.at(i)->ssid()) { + // remove the corresponding accesspoint from configurations + apPath = accessPoints.at(i)->connectionInterface()->path(); + QNetworkConfigurationPrivatePointer ptr + = accessPointConfigurations.take(apPath); + if (ptr) { + locker.unlock(); + emit configurationRemoved(ptr); + locker.relock(); + } + } + } + if (!configuredAccessPoints.contains(settingsPath)) + configuredAccessPoints.insert(apPath,settingsPath); + } QNetworkConfigurationPrivate *cpPriv = parseConnection(settingsPath, connection->getSettings()); @@ -476,9 +526,21 @@ void QNetworkManagerEngine::newConnection(const QDBusObjectPath &path, break; } } + if (deviceType == DEVICE_TYPE_ETHERNET) { + QHashIterator i(interfaceDevices); + while (i.hasNext()) { + i.next(); + if (i.value()->deviceType() == deviceType) { + QNetworkManagerInterfaceDeviceWired *wiredDevice + = wiredDevices.value(i.value()->connectionInterface()->path()); + if (wiredDevice->carrier()) { + cpPriv->state |= QNetworkConfiguration::Discovered; + } + } + } + } QNetworkConfigurationPrivatePointer ptr(cpPriv); accessPointConfigurations.insert(ptr->id, ptr); - locker.unlock(); emit configurationAdded(ptr); } @@ -524,8 +586,6 @@ void QNetworkManagerEngine::updateConnection() qobject_cast(sender()); if (!connection) return; - - connection->deleteLater(); const QString settingsPath = connection->connectionInterface()->path(); QNetworkConfigurationPrivate *cpPriv = parseConnection(settingsPath, connection->getSettings()); @@ -718,8 +778,8 @@ QNetworkConfigurationPrivate *QNetworkManagerEngine::parseConnection(const QStri foreach (const QDBusObjectPath &devicePath, managerInterface->getDevices()) { QNetworkManagerInterfaceDevice device(devicePath.path(),this); if (device.deviceType() == DEVICE_TYPE_ETHERNET) { - QNetworkManagerInterfaceDeviceWired wiredDevice(device.connectionInterface()->path(),this); - if (wiredDevice.carrier()) { + QNetworkManagerInterfaceDeviceWired *wiredDevice = wiredDevices.value(device.connectionInterface()->path()); + if (wiredDevice->carrier()) { cpPriv->state |= QNetworkConfiguration::Discovered; break; } diff --git a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.h b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.h index 84c0b21b6c..671ed80dab 100644 --- a/src/plugins/bearer/networkmanager/qnetworkmanagerengine.h +++ b/src/plugins/bearer/networkmanager/qnetworkmanagerengine.h @@ -107,6 +107,8 @@ private Q_SLOTS: void removeAccessPoint(const QString &path); void scanFinished(); + void wiredCarrierChanged(bool); + private: QNetworkConfigurationPrivate *parseConnection(const QString &settingsPath, const QNmSettingsMap &map); @@ -114,7 +116,9 @@ private: QNetworkManagerInterface *managerInterface; QNetworkManagerSettings *systemSettings; + QHash wiredDevices; QHash wirelessDevices; + QHash activeConnectionsList; QList connections; QList accessPoints; diff --git a/src/plugins/bearer/networkmanager/qnetworkmanagerservice.cpp b/src/plugins/bearer/networkmanager/qnetworkmanagerservice.cpp index 2d54fa3029..dd7000bfb8 100644 --- a/src/plugins/bearer/networkmanager/qnetworkmanagerservice.cpp +++ b/src/plugins/bearer/networkmanager/qnetworkmanagerservice.cpp @@ -609,12 +609,32 @@ bool QNetworkManagerInterfaceDeviceWired::carrier() const return false; } +QStringList QNetworkManagerInterfaceDeviceWired::availableConnections() +{ + QStringList list; + if (propertyMap.contains("AvailableConnections")) { + const QDBusArgument &dbusArgs = propertyMap.value("Carrier").value(); + QDBusObjectPath path; + dbusArgs.beginArray(); + while (!dbusArgs.atEnd()) { + dbusArgs >> path; + list << path.path(); + } + dbusArgs.endArray(); + } + + return list; +} + void QNetworkManagerInterfaceDeviceWired::propertiesSwap(QMap map) { QMapIterator i(map); while (i.hasNext()) { i.next(); propertyMap.insert(i.key(),i.value()); + if (i.key() == QStringLiteral("Carrier")) { + Q_EMIT carrierChanged(i.value().toBool()); + } } Q_EMIT propertiesChanged(map); } @@ -1231,24 +1251,20 @@ QDBusObjectPath QNetworkManagerConnectionActive::specificObject() const return QDBusObjectPath(); } -QList QNetworkManagerConnectionActive::devices() const +QStringList QNetworkManagerConnectionActive::devices() const { + QStringList list; if (propertyMap.contains("Devices")) { const QDBusArgument &dbusArgs = propertyMap.value("Devices").value(); QDBusObjectPath path; - QList list; dbusArgs.beginArray(); while (!dbusArgs.atEnd()) { dbusArgs >> path; - list.append(path); + list.append(path.path()); } dbusArgs.endArray(); - - return list; } - QList list; - list << QDBusObjectPath(); return list; } diff --git a/src/plugins/bearer/networkmanager/qnetworkmanagerservice.h b/src/plugins/bearer/networkmanager/qnetworkmanagerservice.h index df4e5d49e1..5e3c1c85f1 100644 --- a/src/plugins/bearer/networkmanager/qnetworkmanagerservice.h +++ b/src/plugins/bearer/networkmanager/qnetworkmanagerservice.h @@ -305,10 +305,12 @@ public: bool carrier() const; bool setConnections(); bool isValid(); + QStringList availableConnections(); Q_SIGNALS: void propertiesChanged(QMap); void propertiesReady(); + void carrierChanged(bool); private Q_SLOTS: void propertiesSwap(QMap); @@ -494,7 +496,7 @@ public: QDBusInterface *connectionInterface() const; QDBusObjectPath connection() const; QDBusObjectPath specificObject() const; - QList devices() const; + QStringList devices() const; quint32 state() const; bool defaultRoute() const; bool setConnections(); -- cgit v1.2.3