1 /****************************************************************************
3 ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/
6 ** This file is part of the QtNetwork module of the Qt Toolkit.
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** GNU Lesser General Public License Usage
10 ** This file may be used under the terms of the GNU Lesser General Public
11 ** License version 2.1 as published by the Free Software Foundation and
12 ** appearing in the file LICENSE.LGPL included in the packaging of this
13 ** file. Please review the following information to ensure the GNU Lesser
14 ** General Public License version 2.1 requirements will be met:
15 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
17 ** In addition, as a special exception, Nokia gives you certain additional
18 ** rights. These rights are described in the Nokia Qt LGPL Exception
19 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
21 ** GNU General Public License Usage
22 ** Alternatively, this file may be used under the terms of the GNU General
23 ** Public License version 3.0 as published by the Free Software Foundation
24 ** and appearing in the file LICENSE.GPL included in the packaging of this
25 ** file. Please review the following information to ensure the GNU General
26 ** Public License version 3.0 requirements will be met:
27 ** http://www.gnu.org/copyleft/gpl.html.
30 ** Alternatively, this file may be used in accordance with the terms and
31 ** conditions contained in a signed written agreement between you and Nokia.
40 ****************************************************************************/
42 #include "qnetworkconfigmanager.h"
44 #include "qnetworkconfigmanager_p.h"
45 #include "qbearerengine_p.h"
47 #include <QtCore/qstringlist.h>
48 #include <QtCore/qcoreapplication.h>
49 #include <QtCore/qmutex.h>
50 #include <QtCore/qthread.h>
51 #include <QtCore/private/qcoreapplication_p.h>
53 #ifndef QT_NO_BEARERMANAGEMENT
57 static QBasicAtomicPointer<QNetworkConfigurationManagerPrivate> connManager_ptr;
59 static void connManager_cleanup()
61 // this is not atomic or thread-safe!
62 QNetworkConfigurationManagerPrivate *cmp = connManager_ptr.fetchAndStoreAcquire(0);
67 void QNetworkConfigurationManagerPrivate::addPostRoutine()
69 qAddPostRoutine(connManager_cleanup);
72 QNetworkConfigurationManagerPrivate *qNetworkConfigurationManagerPrivate()
74 QNetworkConfigurationManagerPrivate *ptr = connManager_ptr.loadAcquire();
76 static QBasicMutex connManager_mutex;
77 QMutexLocker locker(&connManager_mutex);
78 if (!(ptr = connManager_ptr.loadAcquire())) {
79 ptr = new QNetworkConfigurationManagerPrivate;
81 if (QCoreApplicationPrivate::mainThread() == QThread::currentThread()) {
82 // right thread or no main thread yet
83 ptr->addPostRoutine();
86 // wrong thread, we need to make the main thread do this
87 QObject *obj = new QObject;
88 QObject::connect(obj, SIGNAL(destroyed()), ptr, SLOT(addPostRoutine()), Qt::DirectConnection);
89 ptr->initialize(); // this moves us to the right thread
90 obj->moveToThread(QCoreApplicationPrivate::mainThread());
94 connManager_ptr.storeRelease(ptr);
101 \class QNetworkConfigurationManager
103 \brief The QNetworkConfigurationManager class manages the network configurations provided
111 QNetworkConfigurationManager provides access to the network configurations known to the system and
112 enables applications to detect the system capabilities (with regards to network sessions) at runtime.
114 A QNetworkConfiguration abstracts a set of configuration options describing how a
115 network interface has to be configured to connect to a particular target network.
116 QNetworkConfigurationManager maintains and updates the global list of
117 QNetworkConfigurations. Applications can access and filter this list via
118 allConfigurations(). If a new configuration is added or an existing one is removed or changed
119 the configurationAdded(), configurationRemoved() and configurationChanged() signals are emitted
122 The defaultConfiguration() can be used when intending to immediately create a new
123 network session without caring about the particular configuration. It returns
124 a \l QNetworkConfiguration::Discovered configuration. If there are not any
125 discovered ones an invalid configuration is returned.
127 Some configuration updates may require some time to perform updates. A WLAN scan is
128 such an example. Unless the platform performs internal updates it may be required to
129 manually trigger configuration updates via QNetworkConfigurationManager::updateConfigurations().
130 The completion of the update process is indicted by emitting the updateCompleted()
131 signal. The update process ensures that every existing QNetworkConfiguration instance
132 is updated. There is no need to ask for a renewed configuration list via allConfigurations().
134 \sa QNetworkConfiguration
138 \fn void QNetworkConfigurationManager::configurationAdded(const QNetworkConfiguration &config)
140 This signal is emitted whenever a new network configuration is added to the system. The new
141 configuration is specified by \a config.
145 \fn void QNetworkConfigurationManager::configurationRemoved(const QNetworkConfiguration &config)
147 This signal is emitted when a configuration is about to be removed from the system. The removed
148 configuration, specified by \a config, is invalid but retains name and identifier.
152 \fn void QNetworkConfigurationManager::updateCompleted()
154 This signal is emitted when the configuration update has been completed. Such an update can
155 be initiated via \l updateConfigurations().
158 /*! \fn void QNetworkConfigurationManager::configurationChanged(const QNetworkConfiguration &config)
160 This signal is emitted when the \l {QNetworkConfiguration::state()}{state} of \a config changes.
164 \fn void QNetworkConfigurationManager::onlineStateChanged(bool isOnline)
166 This signal is emitted when the device changes from online to offline mode or vice versa.
167 \a isOnline represents the new state of the device.
169 The state is considered to be online for as long as
170 \l{allConfigurations()}{allConfigurations}(QNetworkConfiguration::Active) returns a list with
175 \enum QNetworkConfigurationManager::Capability
177 Specifies the system capabilities of the bearer API. The possible values are:
179 \value CanStartAndStopInterfaces Network sessions and their underlying access points can be
180 started and stopped. If this flag is not set QNetworkSession
181 can only monitor but not influence the state of access points.
182 On some platforms this feature may require elevated user
183 permissions. This option is platform specific and may not
185 \value DirectConnectionRouting Network sessions and their sockets can be bound to a
186 particular network interface. Any packet that passes through
187 the socket goes to the specified network interface and thus
188 disregards standard routing table entries. This may be useful
189 when two interfaces can reach overlapping IP ranges or an
190 application has specific needs in regards to target networks.
191 This option is platform specific and may not always be
193 \value SystemSessionSupport If this flag is set the underlying platform ensures that a
194 network interface is not shut down until the last network
195 session has been \l{QNetworkSession::close()}{closed()}. This
196 works across multiple processes. If the platform session
197 support is missing this API can only ensure the above behavior
198 for network sessions within the same process.
199 In general mobile platforms have such
200 support whereas most desktop platform lack this capability.
201 \value ApplicationLevelRoaming The system gives applications control over the systems roaming
202 behavior. Applications can initiate roaming (in case the
203 current link is not suitable) and are consulted if the system
204 has identified a more suitable access point.
205 \value ForcedRoaming The system disconnects an existing access point and reconnects
206 via a more suitable one. The application does not have any
207 control over this process and has to reconnect its active
209 \value DataStatistics If this flag is set QNetworkSession can provide statistics
210 about transmitted and received data.
211 \value NetworkSessionRequired If this flag is set the platform requires that a network
212 session is created before network operations can be performed.
216 Constructs a QNetworkConfigurationManager with the given \a parent.
218 Note that to ensure a valid list of current configurations immediately available, updating
219 is done during construction which causes some delay.
221 QNetworkConfigurationManager::QNetworkConfigurationManager(QObject *parent)
224 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
226 connect(priv, SIGNAL(configurationAdded(QNetworkConfiguration)),
227 this, SIGNAL(configurationAdded(QNetworkConfiguration)));
228 connect(priv, SIGNAL(configurationRemoved(QNetworkConfiguration)),
229 this, SIGNAL(configurationRemoved(QNetworkConfiguration)));
230 connect(priv, SIGNAL(configurationChanged(QNetworkConfiguration)),
231 this, SIGNAL(configurationChanged(QNetworkConfiguration)));
232 connect(priv, SIGNAL(onlineStateChanged(bool)),
233 this, SIGNAL(onlineStateChanged(bool)));
234 connect(priv, SIGNAL(configurationUpdateComplete()),
235 this, SIGNAL(updateCompleted()));
237 priv->enablePolling();
241 Frees the resources associated with the QNetworkConfigurationManager object.
243 QNetworkConfigurationManager::~QNetworkConfigurationManager()
245 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
247 priv->disablePolling();
252 Returns the default configuration to be used. This function always returns a discovered
253 configuration; otherwise an invalid configuration.
255 In some cases it may be required to call updateConfigurations() and wait for the
256 updateCompleted() signal before calling this function.
258 \sa allConfigurations()
260 QNetworkConfiguration QNetworkConfigurationManager::defaultConfiguration() const
262 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
264 return priv->defaultConfiguration();
266 return QNetworkConfiguration();
270 Returns the list of configurations which comply with the given \a filter.
272 By default this function returns all (defined and undefined) configurations.
274 A wireless network with a particular SSID may only be accessible in a
275 certain area despite the fact that the system has a valid configuration
276 for it. Therefore the filter flag may be used to limit the list to
277 discovered and possibly connected configurations only.
279 If \a filter is set to zero this function returns all possible configurations.
281 Note that this function returns the states for all configurations as they are known at
282 the time of this function call. If for instance a configuration of type WLAN is defined
283 the system may have to perform a WLAN scan in order to determine whether it is
284 actually available. To obtain the most accurate state updateConfigurations() should
285 be used to update each configuration's state. Note that such an update may require
286 some time. It's completion is signalled by updateCompleted(). In the absence of a
287 configuration update this function returns the best estimate at the time of the call.
288 Therefore, if WLAN configurations are of interest, it is recommended that
289 updateConfigurations() is called once after QNetworkConfigurationManager
290 instantiation (WLAN scans are too time consuming to perform in constructor).
291 After this the data is kept automatically up-to-date as the system reports
294 QList<QNetworkConfiguration> QNetworkConfigurationManager::allConfigurations(QNetworkConfiguration::StateFlags filter) const
296 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
298 return priv->allConfigurations(filter);
300 return QList<QNetworkConfiguration>();
304 Returns the QNetworkConfiguration for \a identifier; otherwise returns an
305 invalid QNetworkConfiguration.
307 \sa QNetworkConfiguration::identifier()
309 QNetworkConfiguration QNetworkConfigurationManager::configurationFromIdentifier(const QString &identifier) const
311 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
313 return priv->configurationFromIdentifier(identifier);
315 return QNetworkConfiguration();
319 Returns true if the system is considered to be connected to another device via an active
320 network interface; otherwise returns false.
322 This is equivalent to the following code snippet:
324 \snippet code/src_network_bearer_qnetworkconfigmanager.cpp 0
326 \sa onlineStateChanged()
328 bool QNetworkConfigurationManager::isOnline() const
330 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
332 return priv->isOnline();
338 Returns the capabilities supported by the current platform.
340 QNetworkConfigurationManager::Capabilities QNetworkConfigurationManager::capabilities() const
342 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
344 return priv->capabilities();
346 return QNetworkConfigurationManager::Capabilities(0);
350 Initiates an update of all configurations. This may be used to initiate WLAN scans or other
351 time consuming updates which may be required to obtain the correct state for configurations.
353 This call is asynchronous. On completion of this update the updateCompleted() signal is
354 emitted. If new configurations are discovered or old ones were removed or changed the update
355 process may trigger the emission of one or multiple configurationAdded(),
356 configurationRemoved() and configurationChanged() signals.
358 If a configuration state changes as a result of this update all existing QNetworkConfiguration
359 instances are updated automatically.
361 \sa allConfigurations()
363 void QNetworkConfigurationManager::updateConfigurations()
365 QNetworkConfigurationManagerPrivate *priv = qNetworkConfigurationManagerPrivate();
367 priv->performAsyncConfigurationUpdate();
370 #include "moc_qnetworkconfigmanager.cpp"
374 #endif // QT_NO_BEARERMANAGEMENT