mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2026-05-08 10:08:05 +02:00
supplicant: convert NMSupplicantManager to GDBus
(cherry picked from commit 9f5f141100)
This commit is contained in:
parent
fae1a4f864
commit
669b8f70bb
1 changed files with 81 additions and 93 deletions
|
|
@ -29,9 +29,8 @@
|
||||||
|
|
||||||
#include "nm-supplicant-manager.h"
|
#include "nm-supplicant-manager.h"
|
||||||
#include "nm-supplicant-interface.h"
|
#include "nm-supplicant-interface.h"
|
||||||
#include "nm-dbus-manager.h"
|
|
||||||
#include "nm-logging.h"
|
#include "nm-logging.h"
|
||||||
#include "nm-dbus-glib-types.h"
|
#include "nm-core-internal.h"
|
||||||
|
|
||||||
#define NM_SUPPLICANT_MANAGER_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), \
|
#define NM_SUPPLICANT_MANAGER_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), \
|
||||||
NM_TYPE_SUPPLICANT_MANAGER, \
|
NM_TYPE_SUPPLICANT_MANAGER, \
|
||||||
|
|
@ -47,11 +46,10 @@ enum {
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
NMDBusManager * dbus_mgr;
|
GDBusProxy * proxy;
|
||||||
guint name_owner_id;
|
GCancellable * cancellable;
|
||||||
DBusGProxy * proxy;
|
gboolean running;
|
||||||
DBusGProxy * props_proxy;
|
|
||||||
gboolean running;
|
|
||||||
GHashTable * ifaces;
|
GHashTable * ifaces;
|
||||||
gboolean fast_supported;
|
gboolean fast_supported;
|
||||||
ApSupport ap_support;
|
ApSupport ap_support;
|
||||||
|
|
@ -126,35 +124,27 @@ nm_supplicant_manager_iface_release (NMSupplicantManager *self,
|
||||||
/* Ask wpa_supplicant to remove this interface */
|
/* Ask wpa_supplicant to remove this interface */
|
||||||
op = nm_supplicant_interface_get_object_path (iface);
|
op = nm_supplicant_interface_get_object_path (iface);
|
||||||
if (priv->running && priv->proxy && op) {
|
if (priv->running && priv->proxy && op) {
|
||||||
dbus_g_proxy_call_no_reply (priv->proxy, "RemoveInterface",
|
g_dbus_proxy_call (priv->proxy,
|
||||||
DBUS_TYPE_G_OBJECT_PATH, op,
|
"RemoveInterface",
|
||||||
G_TYPE_INVALID);
|
g_variant_new ("(o)", op),
|
||||||
|
G_DBUS_CALL_FLAGS_NONE,
|
||||||
|
3000,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_hash_table_remove (priv->ifaces, ifname);
|
g_hash_table_remove (priv->ifaces, ifname);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
get_capabilities_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_data)
|
update_capabilities (NMSupplicantManager *self)
|
||||||
{
|
{
|
||||||
NMSupplicantManager *self = NM_SUPPLICANT_MANAGER (user_data);
|
|
||||||
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
||||||
NMSupplicantInterface *iface;
|
NMSupplicantInterface *iface;
|
||||||
GHashTableIter hash_iter;
|
GHashTableIter hash_iter;
|
||||||
GError *error = NULL;
|
const char **array;
|
||||||
GHashTable *props = NULL;
|
GVariant *value;
|
||||||
GValue *value;
|
|
||||||
char **iter;
|
|
||||||
|
|
||||||
if (!dbus_g_proxy_end_call (proxy, call_id, &error,
|
|
||||||
DBUS_TYPE_G_MAP_OF_VARIANT, &props,
|
|
||||||
G_TYPE_INVALID)) {
|
|
||||||
nm_log_warn (LOGD_CORE, "Unexpected error requesting supplicant properties: (%d) %s",
|
|
||||||
error ? error->code : -1,
|
|
||||||
error && error->message ? error->message : "(unknown)");
|
|
||||||
g_clear_error (&error);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* The supplicant only advertises global capabilities if the following
|
/* The supplicant only advertises global capabilities if the following
|
||||||
* commit has been applied:
|
* commit has been applied:
|
||||||
|
|
@ -166,13 +156,17 @@ get_capabilities_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_
|
||||||
* dbus: Add global capabilities property
|
* dbus: Add global capabilities property
|
||||||
*/
|
*/
|
||||||
priv->ap_support = AP_SUPPORT_UNKNOWN;
|
priv->ap_support = AP_SUPPORT_UNKNOWN;
|
||||||
value = g_hash_table_lookup (props, "Capabilities");
|
|
||||||
if (value && G_VALUE_HOLDS (value, G_TYPE_STRV)) {
|
value = g_dbus_proxy_get_cached_property (priv->proxy, "Capabilities");
|
||||||
priv->ap_support = AP_SUPPORT_NO;
|
if (value) {
|
||||||
for (iter = g_value_get_boxed (value); iter && *iter; iter++) {
|
if (g_variant_is_of_type (value, G_VARIANT_TYPE_STRING_ARRAY)) {
|
||||||
if (strcasecmp (*iter, "ap") == 0)
|
array = g_variant_get_strv (value, NULL);
|
||||||
|
priv->ap_support = AP_SUPPORT_NO;
|
||||||
|
if (_nm_utils_string_in_list ("ap", array))
|
||||||
priv->ap_support = AP_SUPPORT_YES;
|
priv->ap_support = AP_SUPPORT_YES;
|
||||||
|
g_free (array);
|
||||||
}
|
}
|
||||||
|
g_variant_unref (value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Tell all interfaces about results of the AP check */
|
/* Tell all interfaces about results of the AP check */
|
||||||
|
|
@ -186,28 +180,18 @@ get_capabilities_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_
|
||||||
|
|
||||||
/* EAP-FAST */
|
/* EAP-FAST */
|
||||||
priv->fast_supported = FALSE;
|
priv->fast_supported = FALSE;
|
||||||
value = g_hash_table_lookup (props, "EapMethods");
|
value = g_dbus_proxy_get_cached_property (priv->proxy, "EapMethods");
|
||||||
if (value && G_VALUE_HOLDS (value, G_TYPE_STRV)) {
|
if (value) {
|
||||||
for (iter = g_value_get_boxed (value); iter && *iter; iter++) {
|
if (g_variant_is_of_type (value, G_VARIANT_TYPE_STRING_ARRAY)) {
|
||||||
if (strcasecmp (*iter, "fast") == 0)
|
array = g_variant_get_strv (value, NULL);
|
||||||
|
if (_nm_utils_string_in_list ("fast", array))
|
||||||
priv->fast_supported = TRUE;
|
priv->fast_supported = TRUE;
|
||||||
|
g_free (array);
|
||||||
}
|
}
|
||||||
|
g_variant_unref (value);
|
||||||
}
|
}
|
||||||
|
|
||||||
nm_log_dbg (LOGD_SUPPLICANT, "EAP-FAST is %ssupported", priv->fast_supported ? "" : "not ");
|
nm_log_dbg (LOGD_SUPPLICANT, "EAP-FAST is %ssupported", priv->fast_supported ? "" : "not ");
|
||||||
|
|
||||||
g_hash_table_unref (props);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
check_capabilities (NMSupplicantManager *self)
|
|
||||||
{
|
|
||||||
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
|
||||||
|
|
||||||
dbus_g_proxy_begin_call (priv->props_proxy, "GetAll",
|
|
||||||
get_capabilities_cb, self, NULL,
|
|
||||||
G_TYPE_STRING, WPAS_DBUS_INTERFACE,
|
|
||||||
G_TYPE_INVALID);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
gboolean
|
gboolean
|
||||||
|
|
@ -256,28 +240,21 @@ wpas_die_count_reset_cb (gpointer user_data)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
name_owner_changed (NMDBusManager *dbus_mgr,
|
name_owner_cb (GDBusProxy *proxy, GParamSpec *pspec, gpointer user_data)
|
||||||
const char *name,
|
|
||||||
const char *old_owner,
|
|
||||||
const char *new_owner,
|
|
||||||
gpointer user_data)
|
|
||||||
{
|
{
|
||||||
NMSupplicantManager *self = NM_SUPPLICANT_MANAGER (user_data);
|
NMSupplicantManager *self = NM_SUPPLICANT_MANAGER (user_data);
|
||||||
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
||||||
gboolean old_owner_good = (old_owner && strlen (old_owner));
|
char *owner;
|
||||||
gboolean new_owner_good = (new_owner && strlen (new_owner));
|
|
||||||
|
|
||||||
/* We only care about the supplicant here */
|
g_return_if_fail (proxy == priv->proxy);
|
||||||
if (strcmp (WPAS_DBUS_SERVICE, name) != 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (!old_owner_good && new_owner_good) {
|
owner = g_dbus_proxy_get_name_owner (proxy);
|
||||||
nm_log_info (LOGD_SUPPLICANT, "wpa_supplicant started");
|
nm_log_info (LOGD_SUPPLICANT, "wpa_supplicant %s", owner ? "running" : "stopped");
|
||||||
|
|
||||||
|
if (owner) {
|
||||||
set_running (self, TRUE);
|
set_running (self, TRUE);
|
||||||
check_capabilities (self);
|
update_capabilities (self);
|
||||||
} else if (old_owner_good && !new_owner_good) {
|
} else if (priv->running) {
|
||||||
nm_log_info (LOGD_SUPPLICANT, "wpa_supplicant stopped");
|
|
||||||
|
|
||||||
/* Reschedule the die count reset timeout. Every time the supplicant
|
/* Reschedule the die count reset timeout. Every time the supplicant
|
||||||
* dies we wait 10 seconds before resetting the counter. If the
|
* dies we wait 10 seconds before resetting the counter. If the
|
||||||
* supplicant died more than twice before the timer is reset, then
|
* supplicant died more than twice before the timer is reset, then
|
||||||
|
|
@ -298,6 +275,33 @@ name_owner_changed (NMDBusManager *dbus_mgr,
|
||||||
|
|
||||||
priv->fast_supported = FALSE;
|
priv->fast_supported = FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
g_free (owner);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_proxy_acquired (GObject *object, GAsyncResult *result, gpointer user_data)
|
||||||
|
{
|
||||||
|
NMSupplicantManager *self;
|
||||||
|
NMSupplicantManagerPrivate *priv;
|
||||||
|
GError *error = NULL;
|
||||||
|
GDBusProxy *proxy;
|
||||||
|
|
||||||
|
proxy = g_dbus_proxy_new_for_bus_finish (result, &error);
|
||||||
|
if (!proxy) {
|
||||||
|
nm_log_warn (LOGD_SUPPLICANT,
|
||||||
|
"Failed to acquire wpa_supplicant proxy: Wi-Fi and 802.1x will not be available (%s)",
|
||||||
|
error->message);
|
||||||
|
g_clear_error (&error);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
self = NM_SUPPLICANT_MANAGER (user_data);
|
||||||
|
priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
||||||
|
|
||||||
|
priv->proxy = proxy;
|
||||||
|
g_signal_connect (priv->proxy, "notify::g-name-owner", G_CALLBACK (name_owner_cb), self);
|
||||||
|
name_owner_cb (priv->proxy, NULL, self);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*******************************************************************/
|
/*******************************************************************/
|
||||||
|
|
@ -320,31 +324,19 @@ static void
|
||||||
nm_supplicant_manager_init (NMSupplicantManager *self)
|
nm_supplicant_manager_init (NMSupplicantManager *self)
|
||||||
{
|
{
|
||||||
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
NMSupplicantManagerPrivate *priv = NM_SUPPLICANT_MANAGER_GET_PRIVATE (self);
|
||||||
DBusGConnection *bus;
|
|
||||||
|
|
||||||
priv->dbus_mgr = nm_dbus_manager_get ();
|
|
||||||
priv->name_owner_id = g_signal_connect (priv->dbus_mgr,
|
|
||||||
NM_DBUS_MANAGER_NAME_OWNER_CHANGED,
|
|
||||||
G_CALLBACK (name_owner_changed),
|
|
||||||
self);
|
|
||||||
priv->running = nm_dbus_manager_name_has_owner (priv->dbus_mgr, WPAS_DBUS_SERVICE);
|
|
||||||
|
|
||||||
bus = nm_dbus_manager_get_connection (priv->dbus_mgr);
|
|
||||||
priv->proxy = dbus_g_proxy_new_for_name (bus,
|
|
||||||
WPAS_DBUS_SERVICE,
|
|
||||||
WPAS_DBUS_PATH,
|
|
||||||
WPAS_DBUS_INTERFACE);
|
|
||||||
|
|
||||||
priv->props_proxy = dbus_g_proxy_new_for_name (bus,
|
|
||||||
WPAS_DBUS_SERVICE,
|
|
||||||
WPAS_DBUS_PATH,
|
|
||||||
DBUS_INTERFACE_PROPERTIES);
|
|
||||||
|
|
||||||
priv->ifaces = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref);
|
priv->ifaces = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref);
|
||||||
|
|
||||||
/* Check generic supplicant capabilities */
|
priv->cancellable = g_cancellable_new ();
|
||||||
if (priv->running)
|
g_dbus_proxy_new_for_bus (G_BUS_TYPE_SYSTEM,
|
||||||
check_capabilities (self);
|
G_DBUS_PROXY_FLAGS_NONE,
|
||||||
|
NULL,
|
||||||
|
WPAS_DBUS_SERVICE,
|
||||||
|
WPAS_DBUS_PATH,
|
||||||
|
WPAS_DBUS_INTERFACE,
|
||||||
|
priv->cancellable,
|
||||||
|
(GAsyncReadyCallback) on_proxy_acquired,
|
||||||
|
self);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|
@ -376,17 +368,13 @@ dispose (GObject *object)
|
||||||
priv->die_count_reset_id = 0;
|
priv->die_count_reset_id = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (priv->dbus_mgr) {
|
if (priv->cancellable) {
|
||||||
if (priv->name_owner_id) {
|
g_cancellable_cancel (priv->cancellable);
|
||||||
g_signal_handler_disconnect (priv->dbus_mgr, priv->name_owner_id);
|
g_clear_object (&priv->cancellable);
|
||||||
priv->name_owner_id = 0;
|
|
||||||
}
|
|
||||||
priv->dbus_mgr = NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
g_clear_pointer (&priv->ifaces, g_hash_table_unref);
|
g_clear_pointer (&priv->ifaces, g_hash_table_unref);
|
||||||
g_clear_object (&priv->proxy);
|
g_clear_object (&priv->proxy);
|
||||||
g_clear_object (&priv->props_proxy);
|
|
||||||
|
|
||||||
G_OBJECT_CLASS (nm_supplicant_manager_parent_class)->dispose (object);
|
G_OBJECT_CLASS (nm_supplicant_manager_parent_class)->dispose (object);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue