about summary refs log tree commit diff
path: root/src/nm-core-utils.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/nm-core-utils.c')
-rw-r--r--src/nm-core-utils.c7577
1 files changed, 4037 insertions, 3540 deletions
diff --git a/src/nm-core-utils.c b/src/nm-core-utils.c
index 3950c3c3..7adc011e 100644
--- a/src/nm-core-utils.c
+++ b/src/nm-core-utils.c
@@ -1,4 +1,4 @@
-// SPDX-License-Identifier: GPL-2.0+
+/* SPDX-License-Identifier: GPL-2.0+ */
 /*
  * Copyright (C) 2004 - 2018 Red Hat, Inc.
  * Copyright (C) 2005 - 2008 Novell, Inc.
@@ -36,10 +36,11 @@
 #include "nm-setting-wireless-security.h"
 
 #ifdef __NM_SD_UTILS_H__
-#error "nm-core-utils.c should stay independent of systemd utils. Are you looking for NetworkMangerUtils.c? "
+    #error \
+        "nm-core-utils.c should stay independent of systemd utils. Are you looking for NetworkMangerUtils.c? "
 #endif
 
-G_STATIC_ASSERT (sizeof (NMUtilsTestFlags) <= sizeof (int));
+G_STATIC_ASSERT(sizeof(NMUtilsTestFlags) <= sizeof(int));
 
 /* we read _nm_utils_testing without memory barrier. This is thread-safe,
  * because the static variable is initialized to zero, and only reset
@@ -54,120 +55,120 @@ G_STATIC_ASSERT (sizeof (NMUtilsTestFlags) <= sizeof (int));
 static int _nm_utils_testing = 0;
 
 gboolean
-nm_utils_get_testing_initialized ()
+nm_utils_get_testing_initialized()
 {
-	NMUtilsTestFlags flags;
+    NMUtilsTestFlags flags;
 
-	flags = (NMUtilsTestFlags) _nm_utils_testing;
-	if (flags == NM_UTILS_TEST_NONE)
-		flags = (NMUtilsTestFlags) g_atomic_int_get (&_nm_utils_testing);
-	return flags != NM_UTILS_TEST_NONE;
+    flags = (NMUtilsTestFlags) _nm_utils_testing;
+    if (flags == NM_UTILS_TEST_NONE)
+        flags = (NMUtilsTestFlags) g_atomic_int_get(&_nm_utils_testing);
+    return flags != NM_UTILS_TEST_NONE;
 }
 
 NMUtilsTestFlags
-nm_utils_get_testing ()
+nm_utils_get_testing()
 {
-	NMUtilsTestFlags flags;
+    NMUtilsTestFlags flags;
 
 again:
-	flags = (NMUtilsTestFlags) _nm_utils_testing;
-	if (flags != NM_UTILS_TEST_NONE) {
-		/* Flags already initialized. Return them. */
-		return flags & NM_UTILS_TEST_ALL;
-	}
-
-	/* Accessing nm_utils_get_testing() causes us to set the flags to initialized.
-	 * Detecting running tests also based on g_test_initialized(). */
-	flags = _NM_UTILS_TEST_INITIALIZED;
-	if (g_test_initialized ())
-		flags |= _NM_UTILS_TEST_GENERAL;
-
-	g_atomic_int_compare_and_exchange (&_nm_utils_testing, 0, (int) flags);
-
-	/* regardless of whether we won the race of initializing _nm_utils_testing,
-	 * go back and read the value again. It must be non-zero by now. */
-	goto again;
+    flags = (NMUtilsTestFlags) _nm_utils_testing;
+    if (flags != NM_UTILS_TEST_NONE) {
+        /* Flags already initialized. Return them. */
+        return flags & NM_UTILS_TEST_ALL;
+    }
+
+    /* Accessing nm_utils_get_testing() causes us to set the flags to initialized.
+     * Detecting running tests also based on g_test_initialized(). */
+    flags = _NM_UTILS_TEST_INITIALIZED;
+    if (g_test_initialized())
+        flags |= _NM_UTILS_TEST_GENERAL;
+
+    g_atomic_int_compare_and_exchange(&_nm_utils_testing, 0, (int) flags);
+
+    /* regardless of whether we won the race of initializing _nm_utils_testing,
+     * go back and read the value again. It must be non-zero by now. */
+    goto again;
 }
 
 void
-_nm_utils_set_testing (NMUtilsTestFlags flags)
+_nm_utils_set_testing(NMUtilsTestFlags flags)
 {
-	g_assert (!NM_FLAGS_ANY (flags, ~NM_UTILS_TEST_ALL));
+    g_assert(!NM_FLAGS_ANY(flags, ~NM_UTILS_TEST_ALL));
 
-	/* mask out everything except ALL, and always set GENERAL. */
-	flags = (flags & NM_UTILS_TEST_ALL) | (_NM_UTILS_TEST_GENERAL | _NM_UTILS_TEST_INITIALIZED);
+    /* mask out everything except ALL, and always set GENERAL. */
+    flags = (flags & NM_UTILS_TEST_ALL) | (_NM_UTILS_TEST_GENERAL | _NM_UTILS_TEST_INITIALIZED);
 
-	if (!g_atomic_int_compare_and_exchange (&_nm_utils_testing, 0, (int) flags)) {
-		/* We only allow setting _nm_utils_set_testing() once, before fetching the
-		 * value with nm_utils_get_testing(). */
-		g_return_if_reached ();
-	}
+    if (!g_atomic_int_compare_and_exchange(&_nm_utils_testing, 0, (int) flags)) {
+        /* We only allow setting _nm_utils_set_testing() once, before fetching the
+         * value with nm_utils_get_testing(). */
+        g_return_if_reached();
+    }
 }
 
 /*****************************************************************************/
 
-static GSList *_singletons = NULL;
+static GSList * _singletons          = NULL;
 static gboolean _singletons_shutdown = FALSE;
 
 static void
-_nm_singleton_instance_weak_cb (gpointer data,
-                                GObject *where_the_object_was)
+_nm_singleton_instance_weak_cb(gpointer data, GObject *where_the_object_was)
 {
-	nm_assert (g_slist_find (_singletons, where_the_object_was));
+    nm_assert(g_slist_find(_singletons, where_the_object_was));
 
-	_singletons = g_slist_remove (_singletons, where_the_object_was);
+    _singletons = g_slist_remove(_singletons, where_the_object_was);
 }
 
-static void __attribute__((destructor))
-_nm_singleton_instance_destroy (void)
+static void __attribute__((destructor)) _nm_singleton_instance_destroy(void)
 {
-	_singletons_shutdown = TRUE;
+    _singletons_shutdown = TRUE;
 
-	while (_singletons) {
-		GObject *instance = _singletons->data;
+    while (_singletons) {
+        GObject *instance = _singletons->data;
 
-		_singletons = g_slist_delete_link (_singletons, _singletons);
+        _singletons = g_slist_delete_link(_singletons, _singletons);
 
-		g_object_weak_unref (instance, _nm_singleton_instance_weak_cb, NULL);
+        g_object_weak_unref(instance, _nm_singleton_instance_weak_cb, NULL);
 
-		if (instance->ref_count > 1) {
-			nm_log_dbg (LOGD_CORE, "disown %s singleton ("NM_HASH_OBFUSCATE_PTR_FMT")",
-			            G_OBJECT_TYPE_NAME (instance), NM_HASH_OBFUSCATE_PTR (instance));
-		}
+        if (instance->ref_count > 1) {
+            nm_log_dbg(LOGD_CORE,
+                       "disown %s singleton (" NM_HASH_OBFUSCATE_PTR_FMT ")",
+                       G_OBJECT_TYPE_NAME(instance),
+                       NM_HASH_OBFUSCATE_PTR(instance));
+        }
 
-		g_object_unref (instance);
-	}
+        g_object_unref(instance);
+    }
 }
 
 void
-_nm_singleton_instance_register_destruction (GObject *instance)
+_nm_singleton_instance_register_destruction(GObject *instance)
 {
-	g_return_if_fail (G_IS_OBJECT (instance));
+    g_return_if_fail(G_IS_OBJECT(instance));
 
-	/* Don't allow registration after shutdown. We only destroy the singletons
-	 * once. */
-	g_return_if_fail (!_singletons_shutdown);
+    /* Don't allow registration after shutdown. We only destroy the singletons
+     * once. */
+    g_return_if_fail(!_singletons_shutdown);
 
-	g_object_weak_ref (instance, _nm_singleton_instance_weak_cb, NULL);
+    g_object_weak_ref(instance, _nm_singleton_instance_weak_cb, NULL);
 
-	_singletons = g_slist_prepend (_singletons, instance);
+    _singletons = g_slist_prepend(_singletons, instance);
 }
 
 /*****************************************************************************/
 
 static double
-_exp10 (guint16 ex)
+_exp10(guint16 ex)
 {
-	double v;
+    double v;
 
-	if (ex == 0)
-		return 1.0;
+    if (ex == 0)
+        return 1.0;
 
-	v = _exp10 (ex / 2);
-	v = v * v;
-	if (ex % 2)
-		v *= 10;
-	return v;
+    v = _exp10(ex / 2);
+    v = v * v;
+    if (ex % 2)
+        v *= 10;
+    return v;
 }
 
 /*
@@ -177,11 +178,11 @@ _exp10 (guint16 ex)
  * Returns: 10^ex, or pow(10, ex), or exp10(ex).
  */
 double
-nm_utils_exp10 (gint16 ex)
+nm_utils_exp10(gint16 ex)
 {
-	if (ex >= 0)
-		return _exp10 (ex);
-	return 1.0 / _exp10 (- ((gint32) ex));
+    if (ex >= 0)
+        return _exp10(ex);
+    return 1.0 / _exp10(-((gint32) ex));
 }
 
 /*****************************************************************************/
@@ -196,324 +197,380 @@ nm_utils_exp10 (gint16 ex)
  * Returns: %TRUE if @addr is a valid Ethernet address, %FALSE if it is not.
  */
 gboolean
-nm_ethernet_address_is_valid (gconstpointer addr, gssize len)
+nm_ethernet_address_is_valid(gconstpointer addr, gssize len)
 {
-	guint8 invalid_addr[4][ETH_ALEN] = {
-	    {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF},
-	    {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
-	    {0x44, 0x44, 0x44, 0x44, 0x44, 0x44},
-	    {0x00, 0x30, 0xb4, 0x00, 0x00, 0x00}, /* prism54 dummy MAC */
-	};
-	guint8 addr_bin[ETH_ALEN];
-	guint i;
-
-	if (!addr) {
-		g_return_val_if_fail (len == -1 || len == ETH_ALEN, FALSE);
-		return FALSE;
-	}
-
-	if (len == -1) {
-		if (!nm_utils_hwaddr_aton (addr, addr_bin, ETH_ALEN))
-			return FALSE;
-		addr = addr_bin;
-	} else if (len != ETH_ALEN)
-		g_return_val_if_reached (FALSE);
-
-	/* Check for multicast address */
-	if ((((guint8 *) addr)[0]) & 0x01)
-		return FALSE;
-
-	for (i = 0; i < G_N_ELEMENTS (invalid_addr); i++) {
-		if (nm_utils_hwaddr_matches (addr, ETH_ALEN, invalid_addr[i], ETH_ALEN))
-			return FALSE;
-	}
-
-	return TRUE;
+    guint8 invalid_addr[4][ETH_ALEN] = {
+        {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF},
+        {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
+        {0x44, 0x44, 0x44, 0x44, 0x44, 0x44},
+        {0x00, 0x30, 0xb4, 0x00, 0x00, 0x00}, /* prism54 dummy MAC */
+    };
+    guint8 addr_bin[ETH_ALEN];
+    guint  i;
+
+    if (!addr) {
+        g_return_val_if_fail(len == -1 || len == ETH_ALEN, FALSE);
+        return FALSE;
+    }
+
+    if (len == -1) {
+        if (!nm_utils_hwaddr_aton(addr, addr_bin, ETH_ALEN))
+            return FALSE;
+        addr = addr_bin;
+    } else if (len != ETH_ALEN)
+        g_return_val_if_reached(FALSE);
+
+    /* Check for multicast address */
+    if ((((guint8 *) addr)[0]) & 0x01)
+        return FALSE;
+
+    for (i = 0; i < G_N_ELEMENTS(invalid_addr); i++) {
+        if (nm_utils_hwaddr_matches(addr, ETH_ALEN, invalid_addr[i], ETH_ALEN))
+            return FALSE;
+    }
+
+    return TRUE;
 }
 
 /*****************************************************************************/
 
 void
-nm_utils_array_remove_at_indexes (GArray *array, const guint *indexes_to_delete, gsize len)
+nm_utils_array_remove_at_indexes(GArray *array, const guint *indexes_to_delete, gsize len)
 {
-	gsize elt_size;
-	guint index_to_delete;
-	guint i_src;
-	guint mm_src, mm_dst, mm_len;
-	gsize i_itd;
-	guint res_length;
-
-	g_return_if_fail (array);
-	if (!len)
-		return;
-	g_return_if_fail (indexes_to_delete);
-
-	elt_size = g_array_get_element_size (array);
-
-	i_itd = 0;
-	index_to_delete = indexes_to_delete[0];
-	if (index_to_delete >= array->len)
-		g_return_if_reached ();
-
-	res_length = array->len - 1;
-
-	mm_dst = index_to_delete;
-	mm_src = index_to_delete;
-	mm_len = 0;
-
-	for (i_src = index_to_delete; i_src < array->len; i_src++) {
-		if (i_src < index_to_delete)
-			mm_len++;
-		else {
-			/* we require indexes_to_delete to contain non-repeated, ascending
-			 * indexes. Otherwise we would need to presort the indexes. */
-			while (TRUE) {
-				guint dd;
-
-				if (i_itd + 1 >= len) {
-					index_to_delete = G_MAXUINT;
-					break;
-				}
-
-				dd = indexes_to_delete[++i_itd];
-				if (dd > index_to_delete) {
-					if (dd >= array->len)
-						g_warn_if_reached ();
-					else {
-						g_assert (res_length > 0);
-						res_length--;
-					}
-					index_to_delete = dd;
-					break;
-				}
-				g_warn_if_reached ();
-			}
-
-			if (mm_len) {
-				memmove (&array->data[mm_dst * elt_size],
-				         &array->data[mm_src * elt_size],
-				         mm_len * elt_size);
-				mm_dst += mm_len;
-				mm_src += mm_len + 1;
-				mm_len = 0;
-			} else
-				mm_src++;
-		}
-	}
-	if (mm_len) {
-		memmove (&array->data[mm_dst * elt_size],
-		         &array->data[mm_src * elt_size],
-		         mm_len * elt_size);
-	}
-	g_array_set_size (array, res_length);
+    gsize elt_size;
+    guint index_to_delete;
+    guint i_src;
+    guint mm_src, mm_dst, mm_len;
+    gsize i_itd;
+    guint res_length;
+
+    g_return_if_fail(array);
+    if (!len)
+        return;
+    g_return_if_fail(indexes_to_delete);
+
+    elt_size = g_array_get_element_size(array);
+
+    i_itd           = 0;
+    index_to_delete = indexes_to_delete[0];
+    if (index_to_delete >= array->len)
+        g_return_if_reached();
+
+    res_length = array->len - 1;
+
+    mm_dst = index_to_delete;
+    mm_src = index_to_delete;
+    mm_len = 0;
+
+    for (i_src = index_to_delete; i_src < array->len; i_src++) {
+        if (i_src < index_to_delete)
+            mm_len++;
+        else {
+            /* we require indexes_to_delete to contain non-repeated, ascending
+             * indexes. Otherwise, we would need to presort the indexes. */
+            while (TRUE) {
+                guint dd;
+
+                if (i_itd + 1 >= len) {
+                    index_to_delete = G_MAXUINT;
+                    break;
+                }
+
+                dd = indexes_to_delete[++i_itd];
+                if (dd > index_to_delete) {
+                    if (dd >= array->len)
+                        g_warn_if_reached();
+                    else {
+                        g_assert(res_length > 0);
+                        res_length--;
+                    }
+                    index_to_delete = dd;
+                    break;
+                }
+                g_warn_if_reached();
+            }
+
+            if (mm_len) {
+                memmove(&array->data[mm_dst * elt_size],
+                        &array->data[mm_src * elt_size],
+                        mm_len * elt_size);
+                mm_dst += mm_len;
+                mm_src += mm_len + 1;
+                mm_len = 0;
+            } else
+                mm_src++;
+        }
+    }
+    if (mm_len) {
+        memmove(&array->data[mm_dst * elt_size],
+                &array->data[mm_src * elt_size],
+                mm_len * elt_size);
+    }
+    g_array_set_size(array, res_length);
 }
 
 static const char *
-_trunk_first_line (char *str)
+_trunk_first_line(char *str)
 {
-	char *s;
+    char *s;
 
-	s = strchr (str, '\n');
-	if (s)
-		s[0] = '\0';
-	return str;
+    s = strchr(str, '\n');
+    if (s)
+        s[0] = '\0';
+    return str;
 }
 
 int
-nm_utils_modprobe (GError **error, gboolean suppress_error_logging, const char *arg1, ...)
+nm_utils_modprobe(GError **error, gboolean suppress_error_logging, const char *arg1, ...)
 {
-	gs_unref_ptrarray GPtrArray *argv = NULL;
-	int exit_status;
-	gs_free char *_log_str = NULL;
-#define ARGV_TO_STR(argv)   (_log_str ? _log_str : (_log_str = g_strjoinv (" ", (char **) argv->pdata)))
-	GError *local = NULL;
-	va_list ap;
-	NMLogLevel llevel = suppress_error_logging ? LOGL_DEBUG : LOGL_ERR;
-	gs_free char *std_out = NULL, *std_err = NULL;
-
-	g_return_val_if_fail (!error || !*error, -1);
-	g_return_val_if_fail (arg1, -1);
-
-	/* construct the argument list */
-	argv = g_ptr_array_sized_new (4);
-	g_ptr_array_add (argv, "/sbin/modprobe");
-	g_ptr_array_add (argv, "--use-blacklist");
-	g_ptr_array_add (argv, (char *) arg1);
-
-	va_start (ap, arg1);
-	while ((arg1 = va_arg (ap, const char *)))
-		g_ptr_array_add (argv, (char *) arg1);
-	va_end (ap);
-
-	g_ptr_array_add (argv, NULL);
-
-	nm_log_dbg (LOGD_CORE, "modprobe: '%s'", ARGV_TO_STR (argv));
-	if (!g_spawn_sync (NULL, (char **) argv->pdata, NULL, 0, NULL, NULL, &std_out, &std_err, &exit_status, &local)) {
-		nm_log (llevel, LOGD_CORE, NULL, NULL, "modprobe: '%s' failed: %s", ARGV_TO_STR (argv), local->message);
-		g_propagate_error (error, local);
-		return -1;
-	} else if (exit_status != 0) {
-		nm_log (llevel, LOGD_CORE, NULL, NULL, "modprobe: '%s' exited with error %d%s%s%s%s%s%s", ARGV_TO_STR (argv), exit_status,
-		        std_out&&*std_out ? " (" : "", std_out&&*std_out ? _trunk_first_line (std_out) : "", std_out&&*std_out ? ")" : "",
-		        std_err&&*std_err ? " (" : "", std_err&&*std_err ? _trunk_first_line (std_err) : "", std_err&&*std_err ? ")" : "");
-	}
-
-	return exit_status;
+    gs_unref_ptrarray GPtrArray *argv = NULL;
+    int                          exit_status;
+    gs_free char *               _log_str = NULL;
+#define ARGV_TO_STR(argv) \
+    (_log_str ? _log_str : (_log_str = g_strjoinv(" ", (char **) argv->pdata)))
+    GError *      local = NULL;
+    va_list       ap;
+    NMLogLevel    llevel  = suppress_error_logging ? LOGL_DEBUG : LOGL_ERR;
+    gs_free char *std_out = NULL, *std_err = NULL;
+
+    g_return_val_if_fail(!error || !*error, -1);
+    g_return_val_if_fail(arg1, -1);
+
+    /* construct the argument list */
+    argv = g_ptr_array_sized_new(4);
+    g_ptr_array_add(argv, "/sbin/modprobe");
+    g_ptr_array_add(argv, "--use-blacklist");
+    g_ptr_array_add(argv, (char *) arg1);
+
+    va_start(ap, arg1);
+    while ((arg1 = va_arg(ap, const char *)))
+        g_ptr_array_add(argv, (char *) arg1);
+    va_end(ap);
+
+    g_ptr_array_add(argv, NULL);
+
+    nm_log_dbg(LOGD_CORE, "modprobe: '%s'", ARGV_TO_STR(argv));
+    if (!g_spawn_sync(NULL,
+                      (char **) argv->pdata,
+                      NULL,
+                      0,
+                      NULL,
+                      NULL,
+                      &std_out,
+                      &std_err,
+                      &exit_status,
+                      &local)) {
+        nm_log(llevel,
+               LOGD_CORE,
+               NULL,
+               NULL,
+               "modprobe: '%s' failed: %s",
+               ARGV_TO_STR(argv),
+               local->message);
+        g_propagate_error(error, local);
+        return -1;
+    } else if (exit_status != 0) {
+        nm_log(llevel,
+               LOGD_CORE,
+               NULL,
+               NULL,
+               "modprobe: '%s' exited with error %d%s%s%s%s%s%s",
+               ARGV_TO_STR(argv),
+               exit_status,
+               std_out && *std_out ? " (" : "",
+               std_out && *std_out ? _trunk_first_line(std_out) : "",
+               std_out && *std_out ? ")" : "",
+               std_err && *std_err ? " (" : "",
+               std_err && *std_err ? _trunk_first_line(std_err) : "",
+               std_err && *std_err ? ")" : "");
+    }
+
+    return exit_status;
 }
 
 /*****************************************************************************/
 
 typedef struct {
-	pid_t pid;
-	NMLogDomain log_domain;
-	union {
-		struct {
-			gint64 wait_start_us;
-			guint source_timeout_kill_id;
-		} async;
-		struct {
-			gboolean success;
-			int child_status;
-		} sync;
-	};
-	NMUtilsKillChildAsyncCb callback;
-	void *user_data;
-
-	char log_name[1]; /* variable-length object, must be last element!! */
+    pid_t       pid;
+    NMLogDomain log_domain;
+    union {
+        struct {
+            gint64 wait_start_us;
+            guint  source_timeout_kill_id;
+        } async;
+        struct {
+            gboolean success;
+            int      child_status;
+        } sync;
+    };
+    NMUtilsKillChildAsyncCb callback;
+    void *                  user_data;
+
+    char log_name[1]; /* variable-length object, must be last element!! */
 } KillChildAsyncData;
 
-#define LOG_NAME_FMT "kill child process '%s' (%ld)"
+#define LOG_NAME_FMT         "kill child process '%s' (%ld)"
 #define LOG_NAME_PROCESS_FMT "kill process '%s' (%ld)"
-#define LOG_NAME_ARGS log_name,(long)pid
+#define LOG_NAME_ARGS        log_name, (long) pid
 
 static KillChildAsyncData *
-_kc_async_data_alloc (pid_t pid, NMLogDomain log_domain, const char *log_name, NMUtilsKillChildAsyncCb callback, void *user_data)
+_kc_async_data_alloc(pid_t                   pid,
+                     NMLogDomain             log_domain,
+                     const char *            log_name,
+                     NMUtilsKillChildAsyncCb callback,
+                     void *                  user_data)
 {
-	KillChildAsyncData *data;
-	size_t log_name_len;
+    KillChildAsyncData *data;
+    size_t              log_name_len;
 
-	/* append the name at the end of our KillChildAsyncData. */
-	log_name_len = strlen (LOG_NAME_FMT) + 20 + strlen (log_name);
-	data = g_malloc (sizeof (KillChildAsyncData) - 1 + log_name_len);
-	g_snprintf (data->log_name, log_name_len, LOG_NAME_FMT, LOG_NAME_ARGS);
+    /* append the name at the end of our KillChildAsyncData. */
+    log_name_len = strlen(LOG_NAME_FMT) + 20 + strlen(log_name);
+    data         = g_malloc(sizeof(KillChildAsyncData) - 1 + log_name_len);
+    g_snprintf(data->log_name, log_name_len, LOG_NAME_FMT, LOG_NAME_ARGS);
 
-	data->pid = pid;
-	data->user_data = user_data;
-	data->callback = callback;
-	data->log_domain = log_domain;
+    data->pid        = pid;
+    data->user_data  = user_data;
+    data->callback   = callback;
+    data->log_domain = log_domain;
 
-	return data;
+    return data;
 }
 
 #define KC_EXIT_TO_STRING_BUF_SIZE 128
 static const char *
-_kc_exit_to_string (char *buf, int exit)
-#define _kc_exit_to_string(buf, exit) ( G_STATIC_ASSERT_EXPR(sizeof (buf) == KC_EXIT_TO_STRING_BUF_SIZE && sizeof ((buf)[0]) == 1), _kc_exit_to_string (buf, exit) )
+_kc_exit_to_string(char *buf, int exit)
+#define _kc_exit_to_string(buf, exit)                                                          \
+    (G_STATIC_ASSERT_EXPR(sizeof(buf) == KC_EXIT_TO_STRING_BUF_SIZE && sizeof((buf)[0]) == 1), \
+     _kc_exit_to_string(buf, exit))
 {
-	if (WIFEXITED (exit))
-		g_snprintf (buf, KC_EXIT_TO_STRING_BUF_SIZE, "normally with status %d", WEXITSTATUS (exit));
-	else if (WIFSIGNALED (exit))
-		g_snprintf (buf, KC_EXIT_TO_STRING_BUF_SIZE, "by signal %d", WTERMSIG (exit));
-	else
-		g_snprintf (buf, KC_EXIT_TO_STRING_BUF_SIZE, "with unexpected status %d", exit);
-	return buf;
+    if (WIFEXITED(exit))
+        g_snprintf(buf, KC_EXIT_TO_STRING_BUF_SIZE, "normally with status %d", WEXITSTATUS(exit));
+    else if (WIFSIGNALED(exit))
+        g_snprintf(buf, KC_EXIT_TO_STRING_BUF_SIZE, "by signal %d", WTERMSIG(exit));
+    else
+        g_snprintf(buf, KC_EXIT_TO_STRING_BUF_SIZE, "with unexpected status %d", exit);
+    return buf;
 }
 
 static const char *
-_kc_signal_to_string (int sig)
+_kc_signal_to_string(int sig)
 {
-	switch (sig) {
-	case 0:  return "no signal (0)";
-	case SIGKILL:  return "SIGKILL (" G_STRINGIFY (SIGKILL) ")";
-	case SIGTERM:  return "SIGTERM (" G_STRINGIFY (SIGTERM) ")";
-	default:
-		return "Unexpected signal";
-	}
+    switch (sig) {
+    case 0:
+        return "no signal (0)";
+    case SIGKILL:
+        return "SIGKILL (" G_STRINGIFY(SIGKILL) ")";
+    case SIGTERM:
+        return "SIGTERM (" G_STRINGIFY(SIGTERM) ")";
+    default:
+        return "Unexpected signal";
+    }
 }
 
 #define KC_WAITED_TO_STRING 100
 static const char *
-_kc_waited_to_string (char *buf, gint64 wait_start_us)
-#define _kc_waited_to_string(buf, wait_start_us) ( G_STATIC_ASSERT_EXPR(sizeof (buf) == KC_WAITED_TO_STRING && sizeof ((buf)[0]) == 1), _kc_waited_to_string (buf, wait_start_us) )
+_kc_waited_to_string(char *buf, gint64 wait_start_us)
+#define _kc_waited_to_string(buf, wait_start_us)                                        \
+    (G_STATIC_ASSERT_EXPR(sizeof(buf) == KC_WAITED_TO_STRING && sizeof((buf)[0]) == 1), \
+     _kc_waited_to_string(buf, wait_start_us))
 {
-	g_snprintf (buf, KC_WAITED_TO_STRING, " (%ld usec elapsed)", (long) (nm_utils_get_monotonic_timestamp_usec () - wait_start_us));
-	return buf;
+    g_snprintf(buf,
+               KC_WAITED_TO_STRING,
+               " (%ld usec elapsed)",
+               (long) (nm_utils_get_monotonic_timestamp_usec() - wait_start_us));
+    return buf;
 }
 
 static void
-_kc_cb_watch_child (GPid pid, int status, gpointer user_data)
+_kc_cb_watch_child(GPid pid, int status, gpointer user_data)
 {
-	KillChildAsyncData *data = user_data;
-	char buf_exit[KC_EXIT_TO_STRING_BUF_SIZE], buf_wait[KC_WAITED_TO_STRING];
+    KillChildAsyncData *data = user_data;
+    char                buf_exit[KC_EXIT_TO_STRING_BUF_SIZE], buf_wait[KC_WAITED_TO_STRING];
 
-	if (data->async.source_timeout_kill_id)
-		g_source_remove (data->async.source_timeout_kill_id);
+    if (data->async.source_timeout_kill_id)
+        g_source_remove(data->async.source_timeout_kill_id);
 
-	nm_log_dbg (data->log_domain, "%s: terminated %s%s",
-	            data->log_name, _kc_exit_to_string (buf_exit, status),
-	            _kc_waited_to_string (buf_wait, data->async.wait_start_us));
+    nm_log_dbg(data->log_domain,
+               "%s: terminated %s%s",
+               data->log_name,
+               _kc_exit_to_string(buf_exit, status),
+               _kc_waited_to_string(buf_wait, data->async.wait_start_us));
 
-	if (data->callback)
-		data->callback (pid, TRUE, status, data->user_data);
+    if (data->callback)
+        data->callback(pid, TRUE, status, data->user_data);
 
-	g_free (data);
+    g_free(data);
 }
 
 static gboolean
-_kc_cb_timeout_grace_period (void *user_data)
+_kc_cb_timeout_grace_period(void *user_data)
 {
-	KillChildAsyncData *data = user_data;
-	int ret, errsv;
-
-	data->async.source_timeout_kill_id = 0;
-
-	if ((ret = kill (data->pid, SIGKILL)) != 0) {
-		errsv = errno;
-		/* ESRCH means, process does not exist or is already a zombie. */
-		if (errsv != ESRCH) {
-			nm_log_err (LOGD_CORE | data->log_domain, "%s: kill(SIGKILL) returned unexpected return value %d: (%s, %d)",
-			            data->log_name, ret, nm_strerror_native (errsv), errsv);
-		}
-	} else {
-		nm_log_dbg (data->log_domain, "%s: process not terminated after %ld usec. Sending SIGKILL signal",
-		            data->log_name, (long) (nm_utils_get_monotonic_timestamp_usec () - data->async.wait_start_us));
-	}
-
-	return G_SOURCE_REMOVE;
+    KillChildAsyncData *data = user_data;
+    int                 ret, errsv;
+
+    data->async.source_timeout_kill_id = 0;
+
+    if ((ret = kill(data->pid, SIGKILL)) != 0) {
+        errsv = errno;
+        /* ESRCH means, process does not exist or is already a zombie. */
+        if (errsv != ESRCH) {
+            nm_log_err(LOGD_CORE | data->log_domain,
+                       "%s: kill(SIGKILL) returned unexpected return value %d: (%s, %d)",
+                       data->log_name,
+                       ret,
+                       nm_strerror_native(errsv),
+                       errsv);
+        }
+    } else {
+        nm_log_dbg(data->log_domain,
+                   "%s: process not terminated after %ld usec. Sending SIGKILL signal",
+                   data->log_name,
+                   (long) (nm_utils_get_monotonic_timestamp_usec() - data->async.wait_start_us));
+    }
+
+    return G_SOURCE_REMOVE;
 }
 
 static gboolean
-_kc_invoke_callback_idle (gpointer user_data)
+_kc_invoke_callback_idle(gpointer user_data)
 {
-	KillChildAsyncData *data = user_data;
+    KillChildAsyncData *data = user_data;
 
-	if (data->sync.success) {
-		char buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
+    if (data->sync.success) {
+        char buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
 
-		nm_log_dbg (data->log_domain, "%s: invoke callback: terminated %s",
-		            data->log_name, _kc_exit_to_string (buf_exit, data->sync.child_status));
-	} else
-		nm_log_dbg (data->log_domain, "%s: invoke callback: killing child failed", data->log_name);
+        nm_log_dbg(data->log_domain,
+                   "%s: invoke callback: terminated %s",
+                   data->log_name,
+                   _kc_exit_to_string(buf_exit, data->sync.child_status));
+    } else
+        nm_log_dbg(data->log_domain, "%s: invoke callback: killing child failed", data->log_name);
 
-	data->callback (data->pid, data->sync.success, data->sync.child_status, data->user_data);
-	g_free (data);
+    data->callback(data->pid, data->sync.success, data->sync.child_status, data->user_data);
+    g_free(data);
 
-	return G_SOURCE_REMOVE;
+    return G_SOURCE_REMOVE;
 }
 
 static void
-_kc_invoke_callback (pid_t pid, NMLogDomain log_domain, const char *log_name, NMUtilsKillChildAsyncCb callback, void *user_data, gboolean success, int child_status)
+_kc_invoke_callback(pid_t                   pid,
+                    NMLogDomain             log_domain,
+                    const char *            log_name,
+                    NMUtilsKillChildAsyncCb callback,
+                    void *                  user_data,
+                    gboolean                success,
+                    int                     child_status)
 {
-	KillChildAsyncData *data;
+    KillChildAsyncData *data;
 
-	if (!callback)
-		return;
+    if (!callback)
+        return;
 
-	data = _kc_async_data_alloc (pid, log_domain, log_name, callback, user_data);
-	data->sync.success = success;
-	data->sync.child_status = child_status;
+    data                    = _kc_async_data_alloc(pid, log_domain, log_name, callback, user_data);
+    data->sync.success      = success;
+    data->sync.child_status = child_status;
 
-	g_idle_add (_kc_invoke_callback_idle, data);
+    g_idle_add(_kc_invoke_callback_idle, data);
 }
 
 /* nm_utils_kill_child_async:
@@ -534,87 +591,118 @@ _kc_invoke_callback (pid_t pid, NMLogDomain log_domain, const char *log_name, NM
  * supports only one watcher per child.
  **/
 void
-nm_utils_kill_child_async (pid_t pid, int sig, NMLogDomain log_domain,
-                           const char *log_name, guint32 wait_before_kill_msec,
-                           NMUtilsKillChildAsyncCb callback, void *user_data)
+nm_utils_kill_child_async(pid_t                   pid,
+                          int                     sig,
+                          NMLogDomain             log_domain,
+                          const char *            log_name,
+                          guint32                 wait_before_kill_msec,
+                          NMUtilsKillChildAsyncCb callback,
+                          void *                  user_data)
 {
-	int status = 0, errsv;
-	pid_t ret;
-	KillChildAsyncData *data;
-	char buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
-
-	g_return_if_fail (pid > 0);
-	g_return_if_fail (log_name != NULL);
-
-	/* let's see if the child already terminated... */
-	ret = waitpid (pid, &status, WNOHANG);
-	if (ret > 0) {
-		nm_log_dbg (log_domain, LOG_NAME_FMT ": process %ld already terminated %s",
-		            LOG_NAME_ARGS, (long) ret, _kc_exit_to_string (buf_exit, status));
-		_kc_invoke_callback (pid, log_domain, log_name, callback, user_data, TRUE, status);
-		return;
-	} else if (ret != 0) {
-		errsv = errno;
-		/* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
-		if (errsv != ECHILD) {
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": unexpected error while waitpid: %s (%d)",
-			            LOG_NAME_ARGS, nm_strerror_native (errsv), errsv);
-			_kc_invoke_callback (pid, log_domain, log_name, callback, user_data, FALSE, -1);
-			return;
-		}
-	}
-
-	/* send the first signal. */
-	if (kill (pid, sig) != 0) {
-		errsv = errno;
-		/* ESRCH means, process does not exist or is already a zombie. */
-		if (errsv != ESRCH) {
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": unexpected error sending %s: %s (%d)",
-			            LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv);
-			_kc_invoke_callback (pid, log_domain, log_name, callback, user_data, FALSE, -1);
-			return;
-		}
-
-		/* let's try again with waitpid, probably there was a race... */
-		ret = waitpid (pid, &status, 0);
-		if (ret > 0) {
-			nm_log_dbg (log_domain, LOG_NAME_FMT ": process %ld already terminated %s",
-			            LOG_NAME_ARGS, (long) ret, _kc_exit_to_string (buf_exit, status));
-			_kc_invoke_callback (pid, log_domain, log_name, callback, user_data, TRUE, status);
-		} else {
-			errsv = errno;
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": failed due to unexpected return value %ld by waitpid (%s, %d) after sending %s",
-			            LOG_NAME_ARGS, (long) ret, nm_strerror_native (errsv), errsv, _kc_signal_to_string (sig));
-			_kc_invoke_callback (pid, log_domain, log_name, callback, user_data, FALSE, -1);
-		}
-		return;
-	}
-
-	data = _kc_async_data_alloc (pid, log_domain, log_name, callback, user_data);
-	data->async.wait_start_us = nm_utils_get_monotonic_timestamp_usec ();
-
-	if (sig != SIGKILL && wait_before_kill_msec > 0) {
-		data->async.source_timeout_kill_id = g_timeout_add (wait_before_kill_msec, _kc_cb_timeout_grace_period, data);
-		nm_log_dbg (log_domain, "%s: wait for process to terminate after sending %s (send SIGKILL in %ld milliseconds)...",
-		            data->log_name,  _kc_signal_to_string (sig), (long) wait_before_kill_msec);
-	} else {
-		data->async.source_timeout_kill_id = 0;
-		nm_log_dbg (log_domain, "%s: wait for process to terminate after sending %s...",
-		            data->log_name, _kc_signal_to_string (sig));
-	}
-
-	g_child_watch_add (pid, _kc_cb_watch_child, data);
+    int                 status = 0, errsv;
+    pid_t               ret;
+    KillChildAsyncData *data;
+    char                buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
+
+    g_return_if_fail(pid > 0);
+    g_return_if_fail(log_name != NULL);
+
+    /* let's see if the child already terminated... */
+    ret = waitpid(pid, &status, WNOHANG);
+    if (ret > 0) {
+        nm_log_dbg(log_domain,
+                   LOG_NAME_FMT ": process %ld already terminated %s",
+                   LOG_NAME_ARGS,
+                   (long) ret,
+                   _kc_exit_to_string(buf_exit, status));
+        _kc_invoke_callback(pid, log_domain, log_name, callback, user_data, TRUE, status);
+        return;
+    } else if (ret != 0) {
+        errsv = errno;
+        /* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
+        if (errsv != ECHILD) {
+            nm_log_err(LOGD_CORE | log_domain,
+                       LOG_NAME_FMT ": unexpected error while waitpid: %s (%d)",
+                       LOG_NAME_ARGS,
+                       nm_strerror_native(errsv),
+                       errsv);
+            _kc_invoke_callback(pid, log_domain, log_name, callback, user_data, FALSE, -1);
+            return;
+        }
+    }
+
+    /* send the first signal. */
+    if (kill(pid, sig) != 0) {
+        errsv = errno;
+        /* ESRCH means, process does not exist or is already a zombie. */
+        if (errsv != ESRCH) {
+            nm_log_err(LOGD_CORE | log_domain,
+                       LOG_NAME_FMT ": unexpected error sending %s: %s (%d)",
+                       LOG_NAME_ARGS,
+                       _kc_signal_to_string(sig),
+                       nm_strerror_native(errsv),
+                       errsv);
+            _kc_invoke_callback(pid, log_domain, log_name, callback, user_data, FALSE, -1);
+            return;
+        }
+
+        /* let's try again with waitpid, probably there was a race... */
+        ret = waitpid(pid, &status, 0);
+        if (ret > 0) {
+            nm_log_dbg(log_domain,
+                       LOG_NAME_FMT ": process %ld already terminated %s",
+                       LOG_NAME_ARGS,
+                       (long) ret,
+                       _kc_exit_to_string(buf_exit, status));
+            _kc_invoke_callback(pid, log_domain, log_name, callback, user_data, TRUE, status);
+        } else {
+            errsv = errno;
+            nm_log_err(
+                LOGD_CORE | log_domain,
+                LOG_NAME_FMT
+                ": failed due to unexpected return value %ld by waitpid (%s, %d) after sending %s",
+                LOG_NAME_ARGS,
+                (long) ret,
+                nm_strerror_native(errsv),
+                errsv,
+                _kc_signal_to_string(sig));
+            _kc_invoke_callback(pid, log_domain, log_name, callback, user_data, FALSE, -1);
+        }
+        return;
+    }
+
+    data = _kc_async_data_alloc(pid, log_domain, log_name, callback, user_data);
+    data->async.wait_start_us = nm_utils_get_monotonic_timestamp_usec();
+
+    if (sig != SIGKILL && wait_before_kill_msec > 0) {
+        data->async.source_timeout_kill_id =
+            g_timeout_add(wait_before_kill_msec, _kc_cb_timeout_grace_period, data);
+        nm_log_dbg(log_domain,
+                   "%s: wait for process to terminate after sending %s (send SIGKILL in %ld "
+                   "milliseconds)...",
+                   data->log_name,
+                   _kc_signal_to_string(sig),
+                   (long) wait_before_kill_msec);
+    } else {
+        data->async.source_timeout_kill_id = 0;
+        nm_log_dbg(log_domain,
+                   "%s: wait for process to terminate after sending %s...",
+                   data->log_name,
+                   _kc_signal_to_string(sig));
+    }
+
+    g_child_watch_add(pid, _kc_cb_watch_child, data);
 }
 
 static gulong
-_sleep_duration_convert_ms_to_us (guint32 sleep_duration_msec)
+_sleep_duration_convert_ms_to_us(guint32 sleep_duration_msec)
 {
-	if (sleep_duration_msec > 0) {
-		guint64 x = (gint64) sleep_duration_msec * (guint64) 1000L;
+    if (sleep_duration_msec > 0) {
+        guint64 x = (gint64) sleep_duration_msec * (guint64) 1000L;
 
-		return x < G_MAXULONG ? (gulong) x : G_MAXULONG;
-	}
-	return G_USEC_PER_SEC / 20;
+        return x < G_MAXULONG ? (gulong) x : G_MAXULONG;
+    }
+    return G_USEC_PER_SEC / 20;
 }
 
 /* nm_utils_kill_child_sync:
@@ -631,7 +719,7 @@ _sleep_duration_convert_ms_to_us (guint32 sleep_duration_msec)
  * Set to zero, to use the default (meaning 20 wakeups per seconds).
  *
  * Kill a child process synchronously and wait. The function first checks if the child already terminated
- * and if it did, return the exit status. Otherwise send one @sig signal. @sig  will always be
+ * and if it did, return the exit status. Otherwise, send one @sig signal. @sig  will always be
  * sent unless the child already exited. If the child does not exit within @wait_before_kill_msec milliseconds,
  * the function will send %SIGKILL and waits for the child indefinitely. If @wait_before_kill_msec is zero, no
  * %SIGKILL signal will be sent.
@@ -639,158 +727,212 @@ _sleep_duration_convert_ms_to_us (guint32 sleep_duration_msec)
  * In case of error, errno is preserved to contain the last reason of failure.
  **/
 gboolean
-nm_utils_kill_child_sync (pid_t pid, int sig, NMLogDomain log_domain, const char *log_name,
-                          int *child_status, guint32 wait_before_kill_msec,
-                          guint32 sleep_duration_msec)
+nm_utils_kill_child_sync(pid_t       pid,
+                         int         sig,
+                         NMLogDomain log_domain,
+                         const char *log_name,
+                         int *       child_status,
+                         guint32     wait_before_kill_msec,
+                         guint32     sleep_duration_msec)
 {
-	int status = 0, errsv = 0;
-	pid_t ret;
-	gboolean success = FALSE;
-	gboolean was_waiting = FALSE, send_kill = FALSE;
-	char buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
-	char buf_wait[KC_WAITED_TO_STRING];
-	gint64 wait_start_us;
-
-	g_return_val_if_fail (pid > 0, FALSE);
-	g_return_val_if_fail (log_name != NULL, FALSE);
-
-	/* check if the child process already terminated... */
-	ret = waitpid (pid, &status, WNOHANG);
-	if (ret > 0) {
-		nm_log_dbg (log_domain, LOG_NAME_FMT ": process %ld already terminated %s",
-		            LOG_NAME_ARGS, (long) ret, _kc_exit_to_string (buf_exit, status));
-		success = TRUE;
-		goto out;
-	} else if (ret != 0) {
-		errsv = errno;
-		/* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
-		if (errsv != ECHILD) {
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": unexpected error while waitpid: %s (%d)",
-			            LOG_NAME_ARGS, nm_strerror_native (errsv), errsv);
-			goto out;
-		}
-	}
-
-	/* send first signal @sig */
-	if (kill (pid, sig) != 0) {
-		errsv = errno;
-		/* ESRCH means, process does not exist or is already a zombie. */
-		if (errsv != ESRCH) {
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": failed to send %s: %s (%d)",
-			            LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv);
-		} else {
-			/* let's try again with waitpid, probably there was a race... */
-			ret = waitpid (pid, &status, 0);
-			if (ret > 0) {
-				nm_log_dbg (log_domain, LOG_NAME_FMT ": process %ld already terminated %s",
-				            LOG_NAME_ARGS, (long) ret, _kc_exit_to_string (buf_exit, status));
-				success = TRUE;
-			} else {
-				errsv = errno;
-				nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": failed due to unexpected return value %ld by waitpid (%s, %d) after sending %s",
-				            LOG_NAME_ARGS, (long) ret, nm_strerror_native (errsv), errsv, _kc_signal_to_string (sig));
-			}
-		}
-		goto out;
-	}
-
-	wait_start_us = nm_utils_get_monotonic_timestamp_usec ();
-
-	/* wait for the process to terminated... */
-	if (sig != SIGKILL) {
-		gint64 wait_until, now;
-		gulong sleep_time, sleep_duration_usec;
-		int loop_count = 0;
-
-		sleep_duration_usec = _sleep_duration_convert_ms_to_us (sleep_duration_msec);
-		wait_until = wait_before_kill_msec <= 0 ? 0 : wait_start_us + (((gint64) wait_before_kill_msec) * 1000L);
-
-		while (TRUE) {
-			ret = waitpid (pid, &status, WNOHANG);
-			if (ret > 0) {
-				nm_log_dbg (log_domain, LOG_NAME_FMT ": after sending %s, process %ld exited %s%s",
-				            LOG_NAME_ARGS, _kc_signal_to_string (sig), (long) ret, _kc_exit_to_string (buf_exit, status),
-				            was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-				success = TRUE;
-				goto out;
-			}
-			if (ret == -1) {
-				errsv = errno;
-				/* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
-				if (errsv != ECHILD) {
-					nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": after sending %s, waitpid failed with %s (%d)%s",
-					            LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv,
-					           was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-					goto out;
-				}
-			}
-
-			if (!wait_until)
-				break;
-
-			now = nm_utils_get_monotonic_timestamp_usec ();
-			if (now >= wait_until)
-				break;
-
-			if (!was_waiting) {
-				nm_log_dbg (log_domain, LOG_NAME_FMT ": waiting up to %ld milliseconds for process to terminate normally after sending %s...",
-				            LOG_NAME_ARGS, (long) MAX (wait_before_kill_msec, 0), _kc_signal_to_string (sig));
-				was_waiting = TRUE;
-			}
-
-			sleep_time = MIN (wait_until - now, sleep_duration_usec);
-			if (loop_count < 20) {
-				/* At the beginning we expect the process to die fast.
-				 * Limit the sleep time, the limit doubles with every iteration. */
-				sleep_time = MIN (sleep_time, (((guint64) 1) << loop_count) * G_USEC_PER_SEC / 2000);
-				loop_count++;
-			}
-			g_usleep (sleep_time);
-		}
-
-		/* send SIGKILL, if called with @wait_before_kill_msec > 0 */
-		if (wait_until) {
-			nm_log_dbg (log_domain, LOG_NAME_FMT ": sending SIGKILL...", LOG_NAME_ARGS);
-
-			send_kill = TRUE;
-			if (kill (pid, SIGKILL) != 0) {
-				errsv = errno;
-				/* ESRCH means, process does not exist or is already a zombie. */
-				if (errsv != ESRCH) {
-					nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": failed to send SIGKILL (after sending %s), %s (%d)",
-								LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv);
-					goto out;
-				}
-			}
-		}
-	}
-
-	if (!was_waiting) {
-		nm_log_dbg (log_domain, LOG_NAME_FMT ": waiting for process to terminate after sending %s%s...",
-		            LOG_NAME_ARGS, _kc_signal_to_string (sig), send_kill ? " and SIGKILL" : "");
-	}
-
-	/* block until the child terminates. */
-	while ((ret = waitpid (pid, &status, 0)) <= 0) {
-		errsv = errno;
-
-		if (errsv != EINTR) {
-			nm_log_err (LOGD_CORE | log_domain, LOG_NAME_FMT ": after sending %s%s, waitpid failed with %s (%d)%s",
-			            LOG_NAME_ARGS, _kc_signal_to_string (sig), send_kill ? " and SIGKILL" : "", nm_strerror_native (errsv), errsv,
-			            _kc_waited_to_string (buf_wait, wait_start_us));
-			goto out;
-		}
-	}
-
-	nm_log_dbg (log_domain, LOG_NAME_FMT ": after sending %s%s, process %ld exited %s%s",
-	            LOG_NAME_ARGS, _kc_signal_to_string (sig), send_kill ? " and SIGKILL" : "", (long) ret,
-	            _kc_exit_to_string (buf_exit, status), _kc_waited_to_string (buf_wait, wait_start_us));
-	success = TRUE;
+    int      status = 0, errsv = 0;
+    pid_t    ret;
+    gboolean success     = FALSE;
+    gboolean was_waiting = FALSE, send_kill = FALSE;
+    char     buf_exit[KC_EXIT_TO_STRING_BUF_SIZE];
+    char     buf_wait[KC_WAITED_TO_STRING];
+    gint64   wait_start_us;
+
+    g_return_val_if_fail(pid > 0, FALSE);
+    g_return_val_if_fail(log_name != NULL, FALSE);
+
+    /* check if the child process already terminated... */
+    ret = waitpid(pid, &status, WNOHANG);
+    if (ret > 0) {
+        nm_log_dbg(log_domain,
+                   LOG_NAME_FMT ": process %ld already terminated %s",
+                   LOG_NAME_ARGS,
+                   (long) ret,
+                   _kc_exit_to_string(buf_exit, status));
+        success = TRUE;
+        goto out;
+    } else if (ret != 0) {
+        errsv = errno;
+        /* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
+        if (errsv != ECHILD) {
+            nm_log_err(LOGD_CORE | log_domain,
+                       LOG_NAME_FMT ": unexpected error while waitpid: %s (%d)",
+                       LOG_NAME_ARGS,
+                       nm_strerror_native(errsv),
+                       errsv);
+            goto out;
+        }
+    }
+
+    /* send first signal @sig */
+    if (kill(pid, sig) != 0) {
+        errsv = errno;
+        /* ESRCH means, process does not exist or is already a zombie. */
+        if (errsv != ESRCH) {
+            nm_log_err(LOGD_CORE | log_domain,
+                       LOG_NAME_FMT ": failed to send %s: %s (%d)",
+                       LOG_NAME_ARGS,
+                       _kc_signal_to_string(sig),
+                       nm_strerror_native(errsv),
+                       errsv);
+        } else {
+            /* let's try again with waitpid, probably there was a race... */
+            ret = waitpid(pid, &status, 0);
+            if (ret > 0) {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_FMT ": process %ld already terminated %s",
+                           LOG_NAME_ARGS,
+                           (long) ret,
+                           _kc_exit_to_string(buf_exit, status));
+                success = TRUE;
+            } else {
+                errsv = errno;
+                nm_log_err(LOGD_CORE | log_domain,
+                           LOG_NAME_FMT ": failed due to unexpected return value %ld by waitpid "
+                                        "(%s, %d) after sending %s",
+                           LOG_NAME_ARGS,
+                           (long) ret,
+                           nm_strerror_native(errsv),
+                           errsv,
+                           _kc_signal_to_string(sig));
+            }
+        }
+        goto out;
+    }
+
+    wait_start_us = nm_utils_get_monotonic_timestamp_usec();
+
+    /* wait for the process to terminated... */
+    if (sig != SIGKILL) {
+        gint64 wait_until, now;
+        gulong sleep_time, sleep_duration_usec;
+        int    loop_count = 0;
+
+        sleep_duration_usec = _sleep_duration_convert_ms_to_us(sleep_duration_msec);
+        wait_until          = wait_before_kill_msec <= 0
+                                  ? 0
+                                  : wait_start_us + (((gint64) wait_before_kill_msec) * 1000L);
+
+        while (TRUE) {
+            ret = waitpid(pid, &status, WNOHANG);
+            if (ret > 0) {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_FMT ": after sending %s, process %ld exited %s%s",
+                           LOG_NAME_ARGS,
+                           _kc_signal_to_string(sig),
+                           (long) ret,
+                           _kc_exit_to_string(buf_exit, status),
+                           was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+                success = TRUE;
+                goto out;
+            }
+            if (ret == -1) {
+                errsv = errno;
+                /* ECHILD means, the process is not a child/does not exist or it has SIGCHILD blocked. */
+                if (errsv != ECHILD) {
+                    nm_log_err(LOGD_CORE | log_domain,
+                               LOG_NAME_FMT ": after sending %s, waitpid failed with %s (%d)%s",
+                               LOG_NAME_ARGS,
+                               _kc_signal_to_string(sig),
+                               nm_strerror_native(errsv),
+                               errsv,
+                               was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+                    goto out;
+                }
+            }
+
+            if (!wait_until)
+                break;
+
+            now = nm_utils_get_monotonic_timestamp_usec();
+            if (now >= wait_until)
+                break;
+
+            if (!was_waiting) {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_FMT ": waiting up to %ld milliseconds for process to terminate "
+                                        "normally after sending %s...",
+                           LOG_NAME_ARGS,
+                           (long) MAX(wait_before_kill_msec, 0),
+                           _kc_signal_to_string(sig));
+                was_waiting = TRUE;
+            }
+
+            sleep_time = MIN(wait_until - now, sleep_duration_usec);
+            if (loop_count < 20) {
+                /* At the beginning we expect the process to die fast.
+                 * Limit the sleep time, the limit doubles with every iteration. */
+                sleep_time = MIN(sleep_time, (((guint64) 1) << loop_count) * G_USEC_PER_SEC / 2000);
+                loop_count++;
+            }
+            g_usleep(sleep_time);
+        }
+
+        /* send SIGKILL, if called with @wait_before_kill_msec > 0 */
+        if (wait_until) {
+            nm_log_dbg(log_domain, LOG_NAME_FMT ": sending SIGKILL...", LOG_NAME_ARGS);
+
+            send_kill = TRUE;
+            if (kill(pid, SIGKILL) != 0) {
+                errsv = errno;
+                /* ESRCH means, process does not exist or is already a zombie. */
+                if (errsv != ESRCH) {
+                    nm_log_err(LOGD_CORE | log_domain,
+                               LOG_NAME_FMT ": failed to send SIGKILL (after sending %s), %s (%d)",
+                               LOG_NAME_ARGS,
+                               _kc_signal_to_string(sig),
+                               nm_strerror_native(errsv),
+                               errsv);
+                    goto out;
+                }
+            }
+        }
+    }
+
+    if (!was_waiting) {
+        nm_log_dbg(log_domain,
+                   LOG_NAME_FMT ": waiting for process to terminate after sending %s%s...",
+                   LOG_NAME_ARGS,
+                   _kc_signal_to_string(sig),
+                   send_kill ? " and SIGKILL" : "");
+    }
+
+    /* block until the child terminates. */
+    while ((ret = waitpid(pid, &status, 0)) <= 0) {
+        errsv = errno;
+
+        if (errsv != EINTR) {
+            nm_log_err(LOGD_CORE | log_domain,
+                       LOG_NAME_FMT ": after sending %s%s, waitpid failed with %s (%d)%s",
+                       LOG_NAME_ARGS,
+                       _kc_signal_to_string(sig),
+                       send_kill ? " and SIGKILL" : "",
+                       nm_strerror_native(errsv),
+                       errsv,
+                       _kc_waited_to_string(buf_wait, wait_start_us));
+            goto out;
+        }
+    }
+
+    nm_log_dbg(log_domain,
+               LOG_NAME_FMT ": after sending %s%s, process %ld exited %s%s",
+               LOG_NAME_ARGS,
+               _kc_signal_to_string(sig),
+               send_kill ? " and SIGKILL" : "",
+               (long) ret,
+               _kc_exit_to_string(buf_exit, status),
+               _kc_waited_to_string(buf_wait, wait_start_us));
+    success = TRUE;
 out:
-	if (child_status)
-		*child_status = success ? status : -1;
-	errno = success ? 0 : errsv;
-	return success;
+    if (child_status)
+        *child_status = success ? status : -1;
+    errno = success ? 0 : errsv;
+    return success;
 }
 
 /* nm_utils_kill_process_sync:
@@ -817,195 +959,260 @@ out:
  * process with PID @pid is gone, the process is a zombie, or @max_wait_msec expires.
  **/
 void
-nm_utils_kill_process_sync (pid_t pid, guint64 start_time, int sig, NMLogDomain log_domain,
-                            const char *log_name, guint32 wait_before_kill_msec,
-                            guint32 sleep_duration_msec, guint32 max_wait_msec)
+nm_utils_kill_process_sync(pid_t       pid,
+                           guint64     start_time,
+                           int         sig,
+                           NMLogDomain log_domain,
+                           const char *log_name,
+                           guint32     wait_before_kill_msec,
+                           guint32     sleep_duration_msec,
+                           guint32     max_wait_msec)
 {
-	int errsv;
-	guint64 start_time0;
-	gint64 wait_until_sigkill, now, wait_start_us, max_wait_until;
-	gulong sleep_time, sleep_duration_usec;
-	int loop_count = 0;
-	gboolean was_waiting = FALSE;
-	char buf_wait[KC_WAITED_TO_STRING];
-	char p_state;
-
-	g_return_if_fail (pid > 0);
-	g_return_if_fail (log_name != NULL);
-
-	start_time0 = nm_utils_get_start_time_for_pid (pid, &p_state, NULL);
-	if (start_time0 == 0) {
-		nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": cannot kill process %ld because it seems already gone",
-		            LOG_NAME_ARGS, (long int) pid);
-		return;
-	}
-	if (start_time != 0 && start_time != start_time0) {
-		nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": don't kill process %ld because the start_time is unexpectedly %lu instead of %ld",
-		            LOG_NAME_ARGS, (long int) pid, (unsigned long) start_time0, (unsigned long) start_time);
-		return;
-	}
-
-	switch (p_state) {
-	case 'Z':
-	case 'x':
-	case 'X':
-		nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": cannot kill process %ld because it is already a zombie (%c)",
-		            LOG_NAME_ARGS, (long int) pid, p_state);
-		return;
-	default:
-		break;
-	}
-
-	if (kill (pid, sig) != 0) {
-		errsv = errno;
-		/* ESRCH means, process does not exist or is already a zombie. */
-		if (errsv == ESRCH) {
-			nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": failed to send %s because process seems gone",
-			            LOG_NAME_ARGS, _kc_signal_to_string (sig));
-		} else {
-			nm_log_warn (LOGD_CORE | log_domain, LOG_NAME_PROCESS_FMT ": failed to send %s: %s (%d)",
-			             LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv);
-		}
-		return;
-	}
-
-	/* wait for the process to terminate... */
-
-	wait_start_us = nm_utils_get_monotonic_timestamp_usec ();
-
-	sleep_duration_usec = _sleep_duration_convert_ms_to_us (sleep_duration_msec);
-	if (sig != SIGKILL && wait_before_kill_msec)
-		wait_until_sigkill = wait_start_us + (((gint64) wait_before_kill_msec) * 1000L);
-	else
-		wait_until_sigkill = 0;
-	if (max_wait_msec > 0) {
-		max_wait_until = wait_start_us + (((gint64) max_wait_msec) * 1000L);
-		if (wait_until_sigkill > 0 && wait_until_sigkill > max_wait_msec)
-			wait_until_sigkill = 0;
-	} else
-		max_wait_until = 0;
-
-	while (TRUE) {
-		start_time = nm_utils_get_start_time_for_pid (pid, &p_state, NULL);
-
-		if (start_time != start_time0) {
-			nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": process is gone after sending signal %s%s",
-			            LOG_NAME_ARGS, _kc_signal_to_string (sig),
-			            was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-			return;
-		}
-		switch (p_state) {
-		case 'Z':
-		case 'x':
-		case 'X':
-			nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": process is a zombie (%c) after sending signal %s%s",
-			            LOG_NAME_ARGS, p_state, _kc_signal_to_string (sig),
-			            was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-			return;
-		default:
-			break;
-		}
-
-		if (kill (pid, 0) != 0) {
-			errsv = errno;
-			/* ESRCH means, process does not exist or is already a zombie. */
-			if (errsv == ESRCH) {
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": process is gone or a zombie after sending signal %s%s",
-				            LOG_NAME_ARGS, _kc_signal_to_string (sig),
-				            was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-			} else {
-				nm_log_warn (LOGD_CORE | log_domain, LOG_NAME_PROCESS_FMT ": failed to kill(%ld, 0): %s (%d)%s",
-				             LOG_NAME_ARGS, (long int) pid, nm_strerror_native (errsv), errsv,
-				             was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-			}
-			return;
-		}
-
-		sleep_time = sleep_duration_usec;
-		now = nm_utils_get_monotonic_timestamp_usec ();
-
-		if (   max_wait_until != 0
-		    && now >= max_wait_until) {
-			if (wait_until_sigkill != 0) {
-				/* wait_before_kill_msec is not larger then max_wait_until but we did not yet send
-				 * SIGKILL. Although we already reached our timeout, we don't want to skip sending
-				 * the signal. Even if we don't wait for the process to disappear. */
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": sending SIGKILL", LOG_NAME_ARGS);
-				kill (pid, SIGKILL);
-			}
-			nm_log_warn (log_domain, LOG_NAME_PROCESS_FMT ": timeout %u msec waiting for process to disappear (after sending %s)%s",
-			             LOG_NAME_ARGS, (unsigned) max_wait_until, _kc_signal_to_string (sig),
-			             was_waiting ? _kc_waited_to_string (buf_wait, wait_start_us) : "");
-			return;
-		}
-
-		if (wait_until_sigkill != 0) {
-			if (now >= wait_until_sigkill) {
-				/* Still not dead. SIGKILL now... */
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": sending SIGKILL", LOG_NAME_ARGS);
-				if (kill (pid, SIGKILL) != 0) {
-					errsv = errno;
-					/* ESRCH means, process does not exist or is already a zombie. */
-					if (errsv != ESRCH) {
-						nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": process is gone or a zombie%s",
-						            LOG_NAME_ARGS, _kc_waited_to_string (buf_wait, wait_start_us));
-					} else {
-						nm_log_warn (LOGD_CORE | log_domain, LOG_NAME_PROCESS_FMT ": failed to send SIGKILL (after sending %s), %s (%d)%s",
-						             LOG_NAME_ARGS, _kc_signal_to_string (sig), nm_strerror_native (errsv), errsv,
-						             _kc_waited_to_string (buf_wait, wait_start_us));
-					}
-					return;
-				}
-				sig = SIGKILL;
-				wait_until_sigkill = 0;
-				loop_count = 0; /* reset the loop_count. Now we really expect the process to die quickly. */
-			} else
-				sleep_time = MIN (wait_until_sigkill - now, sleep_duration_usec);
-		}
-
-		if (!was_waiting) {
-			if (wait_until_sigkill != 0) {
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": waiting up to %ld milliseconds for process to disappear before sending KILL signal after sending %s...",
-				            LOG_NAME_ARGS, (long) wait_before_kill_msec, _kc_signal_to_string (sig));
-			} else if (max_wait_until != 0) {
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": waiting up to %ld milliseconds for process to disappear after sending %s...",
-				            LOG_NAME_ARGS, (long) max_wait_msec, _kc_signal_to_string (sig));
-			} else {
-				nm_log_dbg (log_domain, LOG_NAME_PROCESS_FMT ": waiting for process to disappear after sending %s...",
-				            LOG_NAME_ARGS, _kc_signal_to_string (sig));
-			}
-			was_waiting = TRUE;
-		}
-
-		if (loop_count < 20) {
-			/* At the beginning we expect the process to die fast.
-			 * Limit the sleep time, the limit doubles with every iteration. */
-			sleep_time = MIN (sleep_time, (((guint64) 1) << loop_count) * G_USEC_PER_SEC / 2000);
-			loop_count++;
-		}
-		g_usleep (sleep_time);
-	}
+    int      errsv;
+    guint64  start_time0;
+    gint64   wait_until_sigkill, now, wait_start_us, max_wait_until;
+    gulong   sleep_time, sleep_duration_usec;
+    int      loop_count  = 0;
+    gboolean was_waiting = FALSE;
+    char     buf_wait[KC_WAITED_TO_STRING];
+    char     p_state;
+
+    g_return_if_fail(pid > 0);
+    g_return_if_fail(log_name != NULL);
+
+    start_time0 = nm_utils_get_start_time_for_pid(pid, &p_state, NULL);
+    if (start_time0 == 0) {
+        nm_log_dbg(log_domain,
+                   LOG_NAME_PROCESS_FMT ": cannot kill process %ld because it seems already gone",
+                   LOG_NAME_ARGS,
+                   (long int) pid);
+        return;
+    }
+    if (start_time != 0 && start_time != start_time0) {
+        nm_log_dbg(
+            log_domain,
+            LOG_NAME_PROCESS_FMT
+            ": don't kill process %ld because the start_time is unexpectedly %lu instead of %ld",
+            LOG_NAME_ARGS,
+            (long int) pid,
+            (unsigned long) start_time0,
+            (unsigned long) start_time);
+        return;
+    }
+
+    switch (p_state) {
+    case 'Z':
+    case 'x':
+    case 'X':
+        nm_log_dbg(log_domain,
+                   LOG_NAME_PROCESS_FMT
+                   ": cannot kill process %ld because it is already a zombie (%c)",
+                   LOG_NAME_ARGS,
+                   (long int) pid,
+                   p_state);
+        return;
+    default:
+        break;
+    }
+
+    if (kill(pid, sig) != 0) {
+        errsv = errno;
+        /* ESRCH means, process does not exist or is already a zombie. */
+        if (errsv == ESRCH) {
+            nm_log_dbg(log_domain,
+                       LOG_NAME_PROCESS_FMT ": failed to send %s because process seems gone",
+                       LOG_NAME_ARGS,
+                       _kc_signal_to_string(sig));
+        } else {
+            nm_log_warn(LOGD_CORE | log_domain,
+                        LOG_NAME_PROCESS_FMT ": failed to send %s: %s (%d)",
+                        LOG_NAME_ARGS,
+                        _kc_signal_to_string(sig),
+                        nm_strerror_native(errsv),
+                        errsv);
+        }
+        return;
+    }
+
+    /* wait for the process to terminate... */
+
+    wait_start_us = nm_utils_get_monotonic_timestamp_usec();
+
+    sleep_duration_usec = _sleep_duration_convert_ms_to_us(sleep_duration_msec);
+    if (sig != SIGKILL && wait_before_kill_msec)
+        wait_until_sigkill = wait_start_us + (((gint64) wait_before_kill_msec) * 1000L);
+    else
+        wait_until_sigkill = 0;
+    if (max_wait_msec > 0) {
+        max_wait_until = wait_start_us + (((gint64) max_wait_msec) * 1000L);
+        if (wait_until_sigkill > 0 && wait_until_sigkill > max_wait_msec)
+            wait_until_sigkill = 0;
+    } else
+        max_wait_until = 0;
+
+    while (TRUE) {
+        start_time = nm_utils_get_start_time_for_pid(pid, &p_state, NULL);
+
+        if (start_time != start_time0) {
+            nm_log_dbg(log_domain,
+                       LOG_NAME_PROCESS_FMT ": process is gone after sending signal %s%s",
+                       LOG_NAME_ARGS,
+                       _kc_signal_to_string(sig),
+                       was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+            return;
+        }
+        switch (p_state) {
+        case 'Z':
+        case 'x':
+        case 'X':
+            nm_log_dbg(log_domain,
+                       LOG_NAME_PROCESS_FMT ": process is a zombie (%c) after sending signal %s%s",
+                       LOG_NAME_ARGS,
+                       p_state,
+                       _kc_signal_to_string(sig),
+                       was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+            return;
+        default:
+            break;
+        }
+
+        if (kill(pid, 0) != 0) {
+            errsv = errno;
+            /* ESRCH means, process does not exist or is already a zombie. */
+            if (errsv == ESRCH) {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_PROCESS_FMT
+                           ": process is gone or a zombie after sending signal %s%s",
+                           LOG_NAME_ARGS,
+                           _kc_signal_to_string(sig),
+                           was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+            } else {
+                nm_log_warn(LOGD_CORE | log_domain,
+                            LOG_NAME_PROCESS_FMT ": failed to kill(%ld, 0): %s (%d)%s",
+                            LOG_NAME_ARGS,
+                            (long int) pid,
+                            nm_strerror_native(errsv),
+                            errsv,
+                            was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+            }
+            return;
+        }
+
+        sleep_time = sleep_duration_usec;
+        now        = nm_utils_get_monotonic_timestamp_usec();
+
+        if (max_wait_until != 0 && now >= max_wait_until) {
+            if (wait_until_sigkill != 0) {
+                /* wait_before_kill_msec is not larger then max_wait_until but we did not yet send
+                 * SIGKILL. Although we already reached our timeout, we don't want to skip sending
+                 * the signal. Even if we don't wait for the process to disappear. */
+                nm_log_dbg(log_domain, LOG_NAME_PROCESS_FMT ": sending SIGKILL", LOG_NAME_ARGS);
+                kill(pid, SIGKILL);
+            }
+            nm_log_warn(log_domain,
+                        LOG_NAME_PROCESS_FMT
+                        ": timeout %u msec waiting for process to disappear (after sending %s)%s",
+                        LOG_NAME_ARGS,
+                        (unsigned) max_wait_until,
+                        _kc_signal_to_string(sig),
+                        was_waiting ? _kc_waited_to_string(buf_wait, wait_start_us) : "");
+            return;
+        }
+
+        if (wait_until_sigkill != 0) {
+            if (now >= wait_until_sigkill) {
+                /* Still not dead. SIGKILL now... */
+                nm_log_dbg(log_domain, LOG_NAME_PROCESS_FMT ": sending SIGKILL", LOG_NAME_ARGS);
+                if (kill(pid, SIGKILL) != 0) {
+                    errsv = errno;
+                    /* ESRCH means, process does not exist or is already a zombie. */
+                    if (errsv != ESRCH) {
+                        nm_log_dbg(log_domain,
+                                   LOG_NAME_PROCESS_FMT ": process is gone or a zombie%s",
+                                   LOG_NAME_ARGS,
+                                   _kc_waited_to_string(buf_wait, wait_start_us));
+                    } else {
+                        nm_log_warn(LOGD_CORE | log_domain,
+                                    LOG_NAME_PROCESS_FMT
+                                    ": failed to send SIGKILL (after sending %s), %s (%d)%s",
+                                    LOG_NAME_ARGS,
+                                    _kc_signal_to_string(sig),
+                                    nm_strerror_native(errsv),
+                                    errsv,
+                                    _kc_waited_to_string(buf_wait, wait_start_us));
+                    }
+                    return;
+                }
+                sig                = SIGKILL;
+                wait_until_sigkill = 0;
+                loop_count =
+                    0; /* reset the loop_count. Now we really expect the process to die quickly. */
+            } else
+                sleep_time = MIN(wait_until_sigkill - now, sleep_duration_usec);
+        }
+
+        if (!was_waiting) {
+            if (wait_until_sigkill != 0) {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_PROCESS_FMT
+                           ": waiting up to %ld milliseconds for process to disappear before "
+                           "sending KILL signal after sending %s...",
+                           LOG_NAME_ARGS,
+                           (long) wait_before_kill_msec,
+                           _kc_signal_to_string(sig));
+            } else if (max_wait_until != 0) {
+                nm_log_dbg(
+                    log_domain,
+                    LOG_NAME_PROCESS_FMT
+                    ": waiting up to %ld milliseconds for process to disappear after sending %s...",
+                    LOG_NAME_ARGS,
+                    (long) max_wait_msec,
+                    _kc_signal_to_string(sig));
+            } else {
+                nm_log_dbg(log_domain,
+                           LOG_NAME_PROCESS_FMT
+                           ": waiting for process to disappear after sending %s...",
+                           LOG_NAME_ARGS,
+                           _kc_signal_to_string(sig));
+            }
+            was_waiting = TRUE;
+        }
+
+        if (loop_count < 20) {
+            /* At the beginning we expect the process to die fast.
+             * Limit the sleep time, the limit doubles with every iteration. */
+            sleep_time = MIN(sleep_time, (((guint64) 1) << loop_count) * G_USEC_PER_SEC / 2000);
+            loop_count++;
+        }
+        g_usleep(sleep_time);
+    }
 }
 #undef LOG_NAME_FMT
 #undef LOG_NAME_PROCESS_FMT
 #undef LOG_NAME_ARGS
 
 const char *const NM_PATHS_DEFAULT[] = {
-	PREFIX "/sbin/",
-	PREFIX "/bin/",
-	"/usr/local/sbin/",
-	"/sbin/",
-	"/usr/sbin/",
-	"/usr/local/bin/",
-	"/bin/",
-	"/usr/bin/",
-	NULL,
+    PREFIX "/sbin/",
+    PREFIX "/bin/",
+    "/usr/local/sbin/",
+    "/sbin/",
+    "/usr/sbin/",
+    "/usr/local/bin/",
+    "/bin/",
+    "/usr/bin/",
+    NULL,
 };
 
 const char *
-nm_utils_find_helper (const char *progname, const char *try_first, GError **error)
+nm_utils_find_helper(const char *progname, const char *try_first, GError **error)
 {
-	return nm_utils_file_search_in_paths (progname, try_first, NM_PATHS_DEFAULT, G_FILE_TEST_IS_EXECUTABLE, NULL, NULL, error);
+    return nm_utils_file_search_in_paths(progname,
+                                         try_first,
+                                         NM_PATHS_DEFAULT,
+                                         G_FILE_TEST_IS_EXECUTABLE,
+                                         NULL,
+                                         NULL,
+                                         error);
 }
 
 /*****************************************************************************/
@@ -1019,496 +1226,493 @@ nm_utils_find_helper (const char *progname, const char *try_first, GError **erro
  * and returns the result as absolute path.
  **/
 char *
-nm_utils_read_link_absolute (const char *link_file, GError **error)
+nm_utils_read_link_absolute(const char *link_file, GError **error)
 {
-	char *ln, *dirname, *ln_abs;
-
-	ln = g_file_read_link (link_file, error);
-	if (!ln)
-		return NULL;
-	if (g_path_is_absolute (ln))
-		return ln;
-
-	dirname = g_path_get_dirname (link_file);
-	if (!g_path_is_absolute (dirname)) {
-		gs_free char *current_dir = g_get_current_dir ();
-
-		/* @link_file argument was not an absolute path in the first place.
-		 * That actually may be a bug, because the CWD is not well defined
-		 * in most cases. Anyway, apparently we were able to load the file
-		 * even from a relative path. So, when making the link absolute, we
-		 * also need to prepend the CWD. */
-		ln_abs = g_build_filename (current_dir, dirname, ln, NULL);
-	} else
-		ln_abs = g_build_filename (dirname, ln, NULL);
-	g_free (dirname);
-	g_free (ln);
-	return ln_abs;
+    char *ln, *dirname, *ln_abs;
+
+    ln = g_file_read_link(link_file, error);
+    if (!ln)
+        return NULL;
+    if (g_path_is_absolute(ln))
+        return ln;
+
+    dirname = g_path_get_dirname(link_file);
+    if (!g_path_is_absolute(dirname)) {
+        gs_free char *current_dir = g_get_current_dir();
+
+        /* @link_file argument was not an absolute path in the first place.
+         * That actually may be a bug, because the CWD is not well defined
+         * in most cases. Anyway, apparently we were able to load the file
+         * even from a relative path. So, when making the link absolute, we
+         * also need to prepend the CWD. */
+        ln_abs = g_build_filename(current_dir, dirname, ln, NULL);
+    } else
+        ln_abs = g_build_filename(dirname, ln, NULL);
+    g_free(dirname);
+    g_free(ln);
+    return ln_abs;
 }
 
 /*****************************************************************************/
 
-#define DEVICE_TYPE_TAG                         "type:"
-#define DRIVER_TAG                              "driver:"
-#define DHCP_PLUGIN_TAG                         "dhcp-plugin:"
-#define EXCEPT_TAG                              "except:"
-#define MATCH_TAG_CONFIG_NM_VERSION             "nm-version:"
-#define MATCH_TAG_CONFIG_NM_VERSION_MIN         "nm-version-min:"
-#define MATCH_TAG_CONFIG_NM_VERSION_MAX         "nm-version-max:"
-#define MATCH_TAG_CONFIG_ENV                    "env:"
+#define DEVICE_TYPE_TAG                 "type:"
+#define DRIVER_TAG                      "driver:"
+#define DHCP_PLUGIN_TAG                 "dhcp-plugin:"
+#define EXCEPT_TAG                      "except:"
+#define MATCH_TAG_CONFIG_NM_VERSION     "nm-version:"
+#define MATCH_TAG_CONFIG_NM_VERSION_MIN "nm-version-min:"
+#define MATCH_TAG_CONFIG_NM_VERSION_MAX "nm-version-max:"
+#define MATCH_TAG_CONFIG_ENV            "env:"
 
 typedef struct {
-	const char *interface_name;
-	const char *device_type;
-	const char *driver;
-	const char *driver_version;
-	const char *dhcp_plugin;
-	struct {
-		const char *value;
-		gboolean is_parsed;
-		guint len;
-		guint8 bin[NM_UTILS_HWADDR_LEN_MAX];
-	} hwaddr;
-	struct {
-		const char *value;
-		gboolean is_parsed;
-		guint32 a;
-		guint32 b;
-		guint32 c;
-	} s390_subchannels;
+    const char *interface_name;
+    const char *device_type;
+    const char *driver;
+    const char *driver_version;
+    const char *dhcp_plugin;
+    struct {
+        const char *value;
+        gboolean    is_parsed;
+        guint       len;
+        guint8      bin[NM_UTILS_HWADDR_LEN_MAX];
+    } hwaddr;
+    struct {
+        const char *value;
+        gboolean    is_parsed;
+        guint32     a;
+        guint32     b;
+        guint32     c;
+    } s390_subchannels;
 } MatchDeviceData;
 
 static gboolean
-match_device_s390_subchannels_parse (const char *s390_subchannels, guint32 *out_a, guint32 *out_b, guint32 *out_c)
+match_device_s390_subchannels_parse(const char *s390_subchannels,
+                                    guint32 *   out_a,
+                                    guint32 *   out_b,
+                                    guint32 *   out_c)
 {
-	char buf[30 + 1];
-	const int BUFSIZE = G_N_ELEMENTS (buf) - 1;
-	guint i = 0;
-	char *pa = NULL, *pb = NULL, *pc = NULL;
-	gint64 a, b, c;
-
-	nm_assert (s390_subchannels);
-	nm_assert (out_a);
-	nm_assert (out_b);
-	nm_assert (out_c);
-
-	if (!g_ascii_isxdigit (s390_subchannels[0]))
-		return FALSE;
-
-	/* Get the first channel */
-	for (i = 0; s390_subchannels[i]; i++) {
-		char ch = s390_subchannels[i];
-
-		if (!g_ascii_isxdigit (ch) && ch != '.') {
-			if (ch == ',') {
-				/* FIXME: currently we consider the first channel and ignore
-				 * everything after the first ',' separator. Maybe we should
-				 * validate all present channels? */
-				break;
-			}
-			return FALSE;  /* Invalid chars */
-		}
-		if (i >= BUFSIZE)
-			return FALSE;  /* Too long to be a subchannel */
-		buf[i] = ch;
-	}
-	buf[i] = '\0';
-
-	/* and grab each of its elements, there should be 3 */
-	pa = &buf[0];
-	pb = strchr (pa, '.');
-	if (pb)
-		pc = strchr (pb + 1, '.');
-	if (!pb || !pc)
-		return FALSE;
-	*pb++ = '\0';
-	*pc++ = '\0';
-
-	a = _nm_utils_ascii_str_to_int64 (pa, 16, 0, G_MAXUINT32, -1);
-	if (a == -1)
-		return FALSE;
-	b = _nm_utils_ascii_str_to_int64 (pb, 16, 0, G_MAXUINT32, -1);
-	if (b == -1)
-		return FALSE;
-	c = _nm_utils_ascii_str_to_int64 (pc, 16, 0, G_MAXUINT32, -1);
-	if (c == -1)
-		return FALSE;
-
-	*out_a = (guint32) a;
-	*out_b = (guint32) b;
-	*out_c = (guint32) c;
-	return TRUE;
+    char      buf[30 + 1];
+    const int BUFSIZE = G_N_ELEMENTS(buf) - 1;
+    guint     i       = 0;
+    char *    pa = NULL, *pb = NULL, *pc = NULL;
+    gint64    a, b, c;
+
+    nm_assert(s390_subchannels);
+    nm_assert(out_a);
+    nm_assert(out_b);
+    nm_assert(out_c);
+
+    if (!g_ascii_isxdigit(s390_subchannels[0]))
+        return FALSE;
+
+    /* Get the first channel */
+    for (i = 0; s390_subchannels[i]; i++) {
+        char ch = s390_subchannels[i];
+
+        if (!g_ascii_isxdigit(ch) && ch != '.') {
+            if (ch == ',') {
+                /* FIXME: currently we consider the first channel and ignore
+                 * everything after the first ',' separator. Maybe we should
+                 * validate all present channels? */
+                break;
+            }
+            return FALSE; /* Invalid chars */
+        }
+        if (i >= BUFSIZE)
+            return FALSE; /* Too long to be a subchannel */
+        buf[i] = ch;
+    }
+    buf[i] = '\0';
+
+    /* and grab each of its elements, there should be 3 */
+    pa = &buf[0];
+    pb = strchr(pa, '.');
+    if (pb)
+        pc = strchr(pb + 1, '.');
+    if (!pb || !pc)
+        return FALSE;
+    *pb++ = '\0';
+    *pc++ = '\0';
+
+    a = _nm_utils_ascii_str_to_int64(pa, 16, 0, G_MAXUINT32, -1);
+    if (a == -1)
+        return FALSE;
+    b = _nm_utils_ascii_str_to_int64(pb, 16, 0, G_MAXUINT32, -1);
+    if (b == -1)
+        return FALSE;
+    c = _nm_utils_ascii_str_to_int64(pc, 16, 0, G_MAXUINT32, -1);
+    if (c == -1)
+        return FALSE;
+
+    *out_a = (guint32) a;
+    *out_b = (guint32) b;
+    *out_c = (guint32) c;
+    return TRUE;
 }
 
 static gboolean
-match_data_s390_subchannels_eval (const char *spec_str,
-                                  MatchDeviceData *match_data)
+match_data_s390_subchannels_eval(const char *spec_str, MatchDeviceData *match_data)
 {
-	guint32 a, b, c;
-
-	if (G_UNLIKELY (!match_data->s390_subchannels.is_parsed)) {
-		match_data->s390_subchannels.is_parsed = TRUE;
-
-		if (   !match_data->s390_subchannels.value
-		    || !match_device_s390_subchannels_parse (match_data->s390_subchannels.value,
-		                                             &match_data->s390_subchannels.a,
-		                                             &match_data->s390_subchannels.b,
-		                                             &match_data->s390_subchannels.c)) {
-			match_data->s390_subchannels.value = NULL;
-			return FALSE;
-		}
-	} else if (!match_data->s390_subchannels.value)
-		return FALSE;
-
-	if (!match_device_s390_subchannels_parse (spec_str, &a, &b, &c))
-		return FALSE;
-	return    match_data->s390_subchannels.a == a
-	       && match_data->s390_subchannels.b == b
-	       && match_data->s390_subchannels.c == c;
+    guint32 a, b, c;
+
+    if (G_UNLIKELY(!match_data->s390_subchannels.is_parsed)) {
+        match_data->s390_subchannels.is_parsed = TRUE;
+
+        if (!match_data->s390_subchannels.value
+            || !match_device_s390_subchannels_parse(match_data->s390_subchannels.value,
+                                                    &match_data->s390_subchannels.a,
+                                                    &match_data->s390_subchannels.b,
+                                                    &match_data->s390_subchannels.c)) {
+            match_data->s390_subchannels.value = NULL;
+            return FALSE;
+        }
+    } else if (!match_data->s390_subchannels.value)
+        return FALSE;
+
+    if (!match_device_s390_subchannels_parse(spec_str, &a, &b, &c))
+        return FALSE;
+    return match_data->s390_subchannels.a == a && match_data->s390_subchannels.b == b
+           && match_data->s390_subchannels.c == c;
 }
 
 static gboolean
-match_device_hwaddr_eval (const char *spec_str,
-                          MatchDeviceData *match_data)
+match_device_hwaddr_eval(const char *spec_str, MatchDeviceData *match_data)
 {
-	if (G_UNLIKELY (!match_data->hwaddr.is_parsed)) {
-		match_data->hwaddr.is_parsed = TRUE;
-
-		if (match_data->hwaddr.value) {
-			gsize l;
-
-			if (!_nm_utils_hwaddr_aton (match_data->hwaddr.value, match_data->hwaddr.bin, sizeof (match_data->hwaddr.bin), &l))
-				g_return_val_if_reached (FALSE);
-			match_data->hwaddr.len = l;
-		} else
-			return FALSE;
-	} else if (!match_data->hwaddr.len)
-		return FALSE;
-
-	return nm_utils_hwaddr_matches (spec_str, -1, match_data->hwaddr.bin, match_data->hwaddr.len);
+    if (G_UNLIKELY(!match_data->hwaddr.is_parsed)) {
+        match_data->hwaddr.is_parsed = TRUE;
+
+        if (match_data->hwaddr.value) {
+            gsize l;
+
+            if (!_nm_utils_hwaddr_aton(match_data->hwaddr.value,
+                                       match_data->hwaddr.bin,
+                                       sizeof(match_data->hwaddr.bin),
+                                       &l))
+                g_return_val_if_reached(FALSE);
+            match_data->hwaddr.len = l;
+        } else
+            return FALSE;
+    } else if (!match_data->hwaddr.len)
+        return FALSE;
+
+    return nm_utils_hwaddr_matches(spec_str, -1, match_data->hwaddr.bin, match_data->hwaddr.len);
 }
 
-#define _MATCH_CHECK(spec_str, tag) \
-	({ \
-		gboolean _has = FALSE; \
-		\
-		if (!g_ascii_strncasecmp (spec_str, (""tag""), NM_STRLEN (tag))) { \
-			spec_str += NM_STRLEN (tag); \
-			_has = TRUE; \
-		} \
-		_has; \
-	})
+#define _MATCH_CHECK(spec_str, tag)                                        \
+    ({                                                                     \
+        gboolean _has = FALSE;                                             \
+                                                                           \
+        if (!g_ascii_strncasecmp(spec_str, ("" tag ""), NM_STRLEN(tag))) { \
+            spec_str += NM_STRLEN(tag);                                    \
+            _has = TRUE;                                                   \
+        }                                                                  \
+        _has;                                                              \
+    })
 
 static NMMatchSpecMatchType
-_match_result (gboolean has_except,
-               gboolean has_not_except,
-               gboolean has_match,
-               gboolean has_match_except)
+_match_result(gboolean has_except,
+              gboolean has_not_except,
+              gboolean has_match,
+              gboolean has_match_except)
 {
-	if (   has_except
-	    && !has_not_except) {
-		/* a match spec that only consists of a list of except matches is treated specially. */
-		nm_assert (!has_match);
-		if (has_match_except) {
-			/* one of the "except:" matches matched. The result is an explicit
-			 * negative match. */
-			return NM_MATCH_SPEC_NEG_MATCH;
-		} else {
-			/* none of the "except:" matches matched. The result is a positive match,
-			 * despite there being no positive match. */
-			return NM_MATCH_SPEC_MATCH;
-		}
-	}
-
-	if (has_match_except)
-		return NM_MATCH_SPEC_NEG_MATCH;
-	if (has_match)
-		return NM_MATCH_SPEC_MATCH;
-	return NM_MATCH_SPEC_NO_MATCH;
+    if (has_except && !has_not_except) {
+        /* a match spec that only consists of a list of except matches is treated specially. */
+        nm_assert(!has_match);
+        if (has_match_except) {
+            /* one of the "except:" matches matched. The result is an explicit
+             * negative match. */
+            return NM_MATCH_SPEC_NEG_MATCH;
+        } else {
+            /* none of the "except:" matches matched. The result is a positive match,
+             * despite there being no positive match. */
+            return NM_MATCH_SPEC_MATCH;
+        }
+    }
+
+    if (has_match_except)
+        return NM_MATCH_SPEC_NEG_MATCH;
+    if (has_match)
+        return NM_MATCH_SPEC_MATCH;
+    return NM_MATCH_SPEC_NO_MATCH;
 }
 
 static const char *
-match_except (const char *spec_str, gboolean *out_except)
+match_except(const char *spec_str, gboolean *out_except)
 {
-	if (_MATCH_CHECK (spec_str, EXCEPT_TAG))
-		*out_except = TRUE;
-	else
-		*out_except = FALSE;
-	return spec_str;
+    if (_MATCH_CHECK(spec_str, EXCEPT_TAG))
+        *out_except = TRUE;
+    else
+        *out_except = FALSE;
+    return spec_str;
 }
 
 static gboolean
-match_device_eval (const char *spec_str,
-                   gboolean allow_fuzzy,
-                   MatchDeviceData *match_data)
+match_device_eval(const char *spec_str, gboolean allow_fuzzy, MatchDeviceData *match_data)
 {
-	if (spec_str[0] == '*' && spec_str[1] == '\0')
-		return TRUE;
-
-	if (_MATCH_CHECK (spec_str, DEVICE_TYPE_TAG)) {
-		return    match_data->device_type
-		       && nm_streq (spec_str, match_data->device_type);
-	}
-
-	if (_MATCH_CHECK (spec_str, NM_MATCH_SPEC_MAC_TAG))
-		return match_device_hwaddr_eval (spec_str, match_data);
-
-	if (_MATCH_CHECK (spec_str, NM_MATCH_SPEC_INTERFACE_NAME_TAG)) {
-		gboolean use_pattern = FALSE;
-
-		if (spec_str[0] == '=')
-			spec_str += 1;
-		else {
-			if (spec_str[0] == '~')
-				spec_str += 1;
-			use_pattern = TRUE;
-		}
-
-		if (match_data->interface_name) {
-			if (nm_streq (spec_str, match_data->interface_name))
-				return TRUE;
-			if (use_pattern && g_pattern_match_simple (spec_str, match_data->interface_name))
-				return TRUE;
-		}
-		return FALSE;
-	}
-
-	if (_MATCH_CHECK (spec_str, DRIVER_TAG)) {
-		const char *t;
-
-		if (!match_data->driver)
-			return FALSE;
-
-		/* support:
-		 * 1) "${DRIVER}"
-		 *   In this case, DRIVER may not contain a '/' character.
-		 *   It matches any driver version.
-		 * 2) "${DRIVER}/${DRIVER_VERSION}"
-		 *   In this case, DRIVER may contains '/' but DRIVER_VERSION
-		 *   may not. A '/' in DRIVER_VERSION may be replaced by '?'.
-		 *
-		 * It follows, that "${DRIVER}/""*" is like 1), but allows
-		 * '/' inside DRIVER.
-		 *
-		 * The fields match to what `nmcli -f GENERAL.DRIVER,GENERAL.DRIVER-VERSION device show`
-		 * gives. However, DRIVER matches literally, while DRIVER_VERSION is a glob
-		 * supporting ? and *.
-		 */
-
-		t = strrchr (spec_str, '/');
-
-		if (!t)
-			return nm_streq (spec_str, match_data->driver);
-
-		return    (strncmp (spec_str, match_data->driver, t - spec_str) == 0)
-		       && g_pattern_match_simple (&t[1],
-		                                  match_data->driver_version ?: "");
-	}
-
-	if (_MATCH_CHECK (spec_str, NM_MATCH_SPEC_S390_SUBCHANNELS_TAG))
-		return match_data_s390_subchannels_eval (spec_str, match_data);
-
-	if (_MATCH_CHECK (spec_str, DHCP_PLUGIN_TAG))
-		return nm_streq0 (spec_str, match_data->dhcp_plugin);
-
-	if (allow_fuzzy) {
-		if (match_device_hwaddr_eval (spec_str, match_data))
-			return TRUE;
-		if (   match_data->interface_name
-		    && nm_streq (spec_str, match_data->interface_name))
-			return TRUE;
-	}
-
-	return FALSE;
+    if (spec_str[0] == '*' && spec_str[1] == '\0')
+        return TRUE;
+
+    if (_MATCH_CHECK(spec_str, DEVICE_TYPE_TAG)) {
+        return match_data->device_type && nm_streq(spec_str, match_data->device_type);
+    }
+
+    if (_MATCH_CHECK(spec_str, NM_MATCH_SPEC_MAC_TAG))
+        return match_device_hwaddr_eval(spec_str, match_data);
+
+    if (_MATCH_CHECK(spec_str, NM_MATCH_SPEC_INTERFACE_NAME_TAG)) {
+        gboolean use_pattern = FALSE;
+
+        if (spec_str[0] == '=')
+            spec_str += 1;
+        else {
+            if (spec_str[0] == '~')
+                spec_str += 1;
+            use_pattern = TRUE;
+        }
+
+        if (match_data->interface_name) {
+            if (nm_streq(spec_str, match_data->interface_name))
+                return TRUE;
+            if (use_pattern && g_pattern_match_simple(spec_str, match_data->interface_name))
+                return TRUE;
+        }
+        return FALSE;
+    }
+
+    if (_MATCH_CHECK(spec_str, DRIVER_TAG)) {
+        const char *t;
+
+        if (!match_data->driver)
+            return FALSE;
+
+        /* support:
+         * 1) "${DRIVER}"
+         *   In this case, DRIVER may not contain a '/' character.
+         *   It matches any driver version.
+         * 2) "${DRIVER}/${DRIVER_VERSION}"
+         *   In this case, DRIVER may contains '/' but DRIVER_VERSION
+         *   may not. A '/' in DRIVER_VERSION may be replaced by '?'.
+         *
+         * It follows, that "${DRIVER}/""*" is like 1), but allows
+         * '/' inside DRIVER.
+         *
+         * The fields match to what `nmcli -f GENERAL.DRIVER,GENERAL.DRIVER-VERSION device show`
+         * gives. However, DRIVER matches literally, while DRIVER_VERSION is a glob
+         * supporting ? and *.
+         */
+
+        t = strrchr(spec_str, '/');
+
+        if (!t)
+            return nm_streq(spec_str, match_data->driver);
+
+        return (strncmp(spec_str, match_data->driver, t - spec_str) == 0)
+               && g_pattern_match_simple(&t[1], match_data->driver_version ?: "");
+    }
+
+    if (_MATCH_CHECK(spec_str, NM_MATCH_SPEC_S390_SUBCHANNELS_TAG))
+        return match_data_s390_subchannels_eval(spec_str, match_data);
+
+    if (_MATCH_CHECK(spec_str, DHCP_PLUGIN_TAG))
+        return nm_streq0(spec_str, match_data->dhcp_plugin);
+
+    if (allow_fuzzy) {
+        if (match_device_hwaddr_eval(spec_str, match_data))
+            return TRUE;
+        if (match_data->interface_name && nm_streq(spec_str, match_data->interface_name))
+            return TRUE;
+    }
+
+    return FALSE;
 }
 
 NMMatchSpecMatchType
-nm_match_spec_device (const GSList *specs,
-                      const char *interface_name,
-                      const char *device_type,
-                      const char *driver,
-                      const char *driver_version,
-                      const char *hwaddr,
-                      const char *s390_subchannels,
-                      const char *dhcp_plugin)
+nm_match_spec_device(const GSList *specs,
+                     const char *  interface_name,
+                     const char *  device_type,
+                     const char *  driver,
+                     const char *  driver_version,
+                     const char *  hwaddr,
+                     const char *  s390_subchannels,
+                     const char *  dhcp_plugin)
 {
-	const GSList *iter;
-	gboolean has_match = FALSE;
-	gboolean has_match_except = FALSE;
-	gboolean has_except = FALSE;
-	gboolean has_not_except = FALSE;
-	const char *spec_str;
-	MatchDeviceData match_data = {
-	    .interface_name = interface_name,
-	    .device_type = nm_str_not_empty (device_type),
-	    .driver = nm_str_not_empty (driver),
-	    .driver_version = nm_str_not_empty (driver_version),
-	    .dhcp_plugin = nm_str_not_empty (dhcp_plugin),
-	    .hwaddr = {
-	        .value = hwaddr,
-	    },
-	    .s390_subchannels = {
-	        .value = s390_subchannels,
-	    },
-	};
-
-	nm_assert (!hwaddr || nm_utils_hwaddr_valid (hwaddr, -1));
-
-	if (!specs)
-		return NM_MATCH_SPEC_NO_MATCH;
-
-	for (iter = specs; iter; iter = iter->next) {
-		gboolean except;
-
-		spec_str = iter->data;
-
-		if (!spec_str || !*spec_str)
-			continue;
-
-		spec_str = match_except (spec_str, &except);
-
-		if (except)
-			has_except = TRUE;
-		else
-			has_not_except = TRUE;
-
-		if (   ( except && has_match_except)
-		    || (!except && has_match)) {
-			/* evaluating the match does not give new information. Skip it. */
-			continue;
-		}
-
-		if (!match_device_eval (spec_str,
-		                        !except,
-		                        &match_data))
-			continue;
-
-		if (except)
-			has_match_except = TRUE;
-		else
-			has_match = TRUE;
-	}
-
-	return _match_result (has_except, has_not_except, has_match, has_match_except);
+    const GSList *  iter;
+    gboolean        has_match        = FALSE;
+    gboolean        has_match_except = FALSE;
+    gboolean        has_except       = FALSE;
+    gboolean        has_not_except   = FALSE;
+    const char *    spec_str;
+    MatchDeviceData match_data = {
+        .interface_name = interface_name,
+        .device_type    = nm_str_not_empty(device_type),
+        .driver         = nm_str_not_empty(driver),
+        .driver_version = nm_str_not_empty(driver_version),
+        .dhcp_plugin    = nm_str_not_empty(dhcp_plugin),
+        .hwaddr =
+            {
+                .value = hwaddr,
+            },
+        .s390_subchannels =
+            {
+                .value = s390_subchannels,
+            },
+    };
+
+    nm_assert(!hwaddr || nm_utils_hwaddr_valid(hwaddr, -1));
+
+    if (!specs)
+        return NM_MATCH_SPEC_NO_MATCH;
+
+    for (iter = specs; iter; iter = iter->next) {
+        gboolean except;
+
+        spec_str = iter->data;
+
+        if (!spec_str || !*spec_str)
+            continue;
+
+        spec_str = match_except(spec_str, &except);
+
+        if (except)
+            has_except = TRUE;
+        else
+            has_not_except = TRUE;
+
+        if ((except && has_match_except) || (!except && has_match)) {
+            /* evaluating the match does not give new information. Skip it. */
+            continue;
+        }
+
+        if (!match_device_eval(spec_str, !except, &match_data))
+            continue;
+
+        if (except)
+            has_match_except = TRUE;
+        else
+            has_match = TRUE;
+    }
+
+    return _match_result(has_except, has_not_except, has_match, has_match_except);
 }
 
 static gboolean
-match_config_eval (const char *str, const char *tag, guint cur_nm_version)
+match_config_eval(const char *str, const char *tag, guint cur_nm_version)
 {
-	gs_free char *s_ver = NULL;
-	gs_strfreev char **s_ver_tokens = NULL;
-	int v_maj = -1, v_min = -1, v_mic = -1;
-	guint c_maj = -1, c_min = -1, c_mic = -1;
-	guint n_tokens;
-
-	s_ver = g_strdup (str);
-	g_strstrip (s_ver);
-
-	/* Let's be strict with the accepted format here. No funny stuff!! */
-
-	if (s_ver[strspn (s_ver, ".0123456789")] != '\0')
-		return FALSE;
-
-	s_ver_tokens = g_strsplit (s_ver, ".", -1);
-	n_tokens = g_strv_length (s_ver_tokens);
-	if (n_tokens == 0 || n_tokens > 3)
-		return FALSE;
-
-	v_maj = _nm_utils_ascii_str_to_int64 (s_ver_tokens[0], 10, 0, 0xFFFF, -1);
-	if (v_maj < 0)
-		return FALSE;
-	if (n_tokens >= 2) {
-		v_min = _nm_utils_ascii_str_to_int64 (s_ver_tokens[1], 10, 0, 0xFF, -1);
-		if (v_min < 0)
-			return FALSE;
-	}
-	if (n_tokens >= 3) {
-		v_mic = _nm_utils_ascii_str_to_int64 (s_ver_tokens[2], 10, 0, 0xFF, -1);
-		if (v_mic < 0)
-			return FALSE;
-	}
-
-	nm_decode_version (cur_nm_version, &c_maj, &c_min, &c_mic);
-
-#define CHECK_AND_RETURN_FALSE(cur, val, tag, is_last_digit) \
-	G_STMT_START { \
-		if (!strcmp (tag, MATCH_TAG_CONFIG_NM_VERSION_MIN)) { \
-			if (cur < val) \
-				return FALSE; \
-		} else if (!strcmp (tag, MATCH_TAG_CONFIG_NM_VERSION_MAX)) { \
-			if (cur > val) \
-				return FALSE; \
-		} else { \
-			if (cur != val) \
-				return FALSE; \
-		} \
-		if (!(is_last_digit)) { \
-			if (cur != val) \
-				return FALSE; \
-		} \
-	} G_STMT_END
-	if (v_mic >= 0)
-		CHECK_AND_RETURN_FALSE (c_mic, v_mic, tag, TRUE);
-	if (v_min >= 0)
-		CHECK_AND_RETURN_FALSE (c_min, v_min, tag, v_mic < 0);
-	CHECK_AND_RETURN_FALSE (c_maj, v_maj, tag, v_min < 0);
-	return TRUE;
+    gs_free char *     s_ver        = NULL;
+    gs_strfreev char **s_ver_tokens = NULL;
+    int                v_maj = -1, v_min = -1, v_mic = -1;
+    guint              c_maj = -1, c_min = -1, c_mic = -1;
+    guint              n_tokens;
+
+    s_ver = g_strdup(str);
+    g_strstrip(s_ver);
+
+    /* Let's be strict with the accepted format here. No funny stuff!! */
+
+    if (s_ver[strspn(s_ver, ".0123456789")] != '\0')
+        return FALSE;
+
+    s_ver_tokens = g_strsplit(s_ver, ".", -1);
+    n_tokens     = g_strv_length(s_ver_tokens);
+    if (n_tokens == 0 || n_tokens > 3)
+        return FALSE;
+
+    v_maj = _nm_utils_ascii_str_to_int64(s_ver_tokens[0], 10, 0, 0xFFFF, -1);
+    if (v_maj < 0)
+        return FALSE;
+    if (n_tokens >= 2) {
+        v_min = _nm_utils_ascii_str_to_int64(s_ver_tokens[1], 10, 0, 0xFF, -1);
+        if (v_min < 0)
+            return FALSE;
+    }
+    if (n_tokens >= 3) {
+        v_mic = _nm_utils_ascii_str_to_int64(s_ver_tokens[2], 10, 0, 0xFF, -1);
+        if (v_mic < 0)
+            return FALSE;
+    }
+
+    nm_decode_version(cur_nm_version, &c_maj, &c_min, &c_mic);
+
+#define CHECK_AND_RETURN_FALSE(cur, val, tag, is_last_digit)        \
+    G_STMT_START                                                    \
+    {                                                               \
+        if (!strcmp(tag, MATCH_TAG_CONFIG_NM_VERSION_MIN)) {        \
+            if (cur < val)                                          \
+                return FALSE;                                       \
+        } else if (!strcmp(tag, MATCH_TAG_CONFIG_NM_VERSION_MAX)) { \
+            if (cur > val)                                          \
+                return FALSE;                                       \
+        } else {                                                    \
+            if (cur != val)                                         \
+                return FALSE;                                       \
+        }                                                           \
+        if (!(is_last_digit)) {                                     \
+            if (cur != val)                                         \
+                return FALSE;                                       \
+        }                                                           \
+    }                                                               \
+    G_STMT_END
+    if (v_mic >= 0)
+        CHECK_AND_RETURN_FALSE(c_mic, v_mic, tag, TRUE);
+    if (v_min >= 0)
+        CHECK_AND_RETURN_FALSE(c_min, v_min, tag, v_mic < 0);
+    CHECK_AND_RETURN_FALSE(c_maj, v_maj, tag, v_min < 0);
+    return TRUE;
 }
 
 NMMatchSpecMatchType
-nm_match_spec_config (const GSList *specs, guint cur_nm_version, const char *env)
+nm_match_spec_config(const GSList *specs, guint cur_nm_version, const char *env)
 {
-	const GSList *iter;
-	gboolean has_match = FALSE;
-	gboolean has_match_except = FALSE;
-	gboolean has_except = FALSE;
-	gboolean has_not_except = FALSE;
-
-	if (!specs)
-		return NM_MATCH_SPEC_NO_MATCH;
-
-	for (iter = specs; iter; iter = g_slist_next (iter)) {
-		const char *spec_str = iter->data;
-		gboolean except;
-		gboolean v_match;
-
-		if (!spec_str || !*spec_str)
-			continue;
-
-		spec_str = match_except (spec_str, &except);
-
-		if (except)
-			has_except = TRUE;
-		else
-			has_not_except = TRUE;
-
-		if (   ( except && has_match_except)
-		    || (!except && has_match)) {
-			/* evaluating the match does not give new information. Skip it. */
-			continue;
-		}
-
-		if (_MATCH_CHECK (spec_str, MATCH_TAG_CONFIG_NM_VERSION))
-			v_match = match_config_eval (spec_str, MATCH_TAG_CONFIG_NM_VERSION, cur_nm_version);
-		else if (_MATCH_CHECK (spec_str, MATCH_TAG_CONFIG_NM_VERSION_MIN))
-			v_match = match_config_eval (spec_str, MATCH_TAG_CONFIG_NM_VERSION_MIN, cur_nm_version);
-		else if (_MATCH_CHECK (spec_str, MATCH_TAG_CONFIG_NM_VERSION_MAX))
-			v_match = match_config_eval (spec_str, MATCH_TAG_CONFIG_NM_VERSION_MAX, cur_nm_version);
-		else if (_MATCH_CHECK (spec_str, MATCH_TAG_CONFIG_ENV))
-			v_match = env && env[0] && !strcmp (spec_str, env);
-		else
-			v_match = FALSE;
-
-		if (!v_match)
-			continue;
-
-		if (except)
-			has_match_except = TRUE;
-		else
-			has_match = TRUE;
-	}
-
-	return _match_result (has_except, has_not_except, has_match, has_match_except);
+    const GSList *iter;
+    gboolean      has_match        = FALSE;
+    gboolean      has_match_except = FALSE;
+    gboolean      has_except       = FALSE;
+    gboolean      has_not_except   = FALSE;
+
+    if (!specs)
+        return NM_MATCH_SPEC_NO_MATCH;
+
+    for (iter = specs; iter; iter = g_slist_next(iter)) {
+        const char *spec_str = iter->data;
+        gboolean    except;
+        gboolean    v_match;
+
+        if (!spec_str || !*spec_str)
+            continue;
+
+        spec_str = match_except(spec_str, &except);
+
+        if (except)
+            has_except = TRUE;
+        else
+            has_not_except = TRUE;
+
+        if ((except && has_match_except) || (!except && has_match)) {
+            /* evaluating the match does not give new information. Skip it. */
+            continue;
+        }
+
+        if (_MATCH_CHECK(spec_str, MATCH_TAG_CONFIG_NM_VERSION))
+            v_match = match_config_eval(spec_str, MATCH_TAG_CONFIG_NM_VERSION, cur_nm_version);
+        else if (_MATCH_CHECK(spec_str, MATCH_TAG_CONFIG_NM_VERSION_MIN))
+            v_match = match_config_eval(spec_str, MATCH_TAG_CONFIG_NM_VERSION_MIN, cur_nm_version);
+        else if (_MATCH_CHECK(spec_str, MATCH_TAG_CONFIG_NM_VERSION_MAX))
+            v_match = match_config_eval(spec_str, MATCH_TAG_CONFIG_NM_VERSION_MAX, cur_nm_version);
+        else if (_MATCH_CHECK(spec_str, MATCH_TAG_CONFIG_ENV))
+            v_match = env && env[0] && !strcmp(spec_str, env);
+        else
+            v_match = FALSE;
+
+        if (!v_match)
+            continue;
+
+        if (except)
+            has_match_except = TRUE;
+        else
+            has_match = TRUE;
+    }
+
+    return _match_result(has_except, has_not_except, has_match, has_match_except);
 }
 
 #undef _MATCH_CHECK
@@ -1534,89 +1738,89 @@ nm_match_spec_config (const GSList *specs, guint cur_nm_version, const char *env
  * Returns: (transfer full): the list of device specs.
  */
 GSList *
-nm_match_spec_split (const char *value)
+nm_match_spec_split(const char *value)
 {
-	char *string_value, *p, *q0, *q;
-	GSList *pieces = NULL;
-	int trailing_ws;
-
-	if (!value || !*value)
-		return NULL;
-
-	/* Copied from glibs g_key_file_parse_value_as_string() function
-	 * and adjusted. */
-
-	string_value = g_new (char, strlen (value) + 1);
-
-	p = (char *) value;
-
-	/* skip over leading whitespace */
-	while (g_ascii_isspace (*p))
-		p++;
-
-	q0 = q = string_value;
-	trailing_ws = 0;
-	while (*p) {
-		if (*p == '\\') {
-			p++;
-
-			switch (*p) {
-			case 's':
-				*q = ' ';
-				break;
-			case 'n':
-				*q = '\n';
-				break;
-			case 't':
-				*q = '\t';
-				break;
-			case 'r':
-				*q = '\r';
-				break;
-			case '\\':
-				*q = '\\';
-				break;
-			case '\0':
-				break;
-			default:
-				if (NM_IN_SET (*p, ',', ';'))
-					*q = *p;
-				else {
-					*q++ = '\\';
-					*q = *p;
-				}
-				break;
-			}
-			if (*p == '\0')
-				break;
-			p++;
-			trailing_ws = 0;
-		} else {
-			*q = *p;
-			if (*p == '\0')
-				break;
-			if (g_ascii_isspace (*p)) {
-				trailing_ws++;
-				p++;
-			} else if (NM_IN_SET (*p, ',', ';')) {
-				if (q0 < q - trailing_ws)
-					pieces = g_slist_prepend (pieces, g_strndup (q0, (q - q0) - trailing_ws));
-				q0 = q + 1;
-				p++;
-				trailing_ws = 0;
-				while (g_ascii_isspace (*p))
-					p++;
-			} else
-				p++;
-		}
-		q++;
-	}
-
-	*q = '\0';
-	if (q0 < q - trailing_ws)
-		pieces = g_slist_prepend (pieces, g_strndup (q0, (q - q0) - trailing_ws));
-	g_free (string_value);
-	return g_slist_reverse (pieces);
+    char *  string_value, *p, *q0, *q;
+    GSList *pieces = NULL;
+    int     trailing_ws;
+
+    if (!value || !*value)
+        return NULL;
+
+    /* Copied from glibs g_key_file_parse_value_as_string() function
+     * and adjusted. */
+
+    string_value = g_new(char, strlen(value) + 1);
+
+    p = (char *) value;
+
+    /* skip over leading whitespace */
+    while (g_ascii_isspace(*p))
+        p++;
+
+    q0 = q      = string_value;
+    trailing_ws = 0;
+    while (*p) {
+        if (*p == '\\') {
+            p++;
+
+            switch (*p) {
+            case 's':
+                *q = ' ';
+                break;
+            case 'n':
+                *q = '\n';
+                break;
+            case 't':
+                *q = '\t';
+                break;
+            case 'r':
+                *q = '\r';
+                break;
+            case '\\':
+                *q = '\\';
+                break;
+            case '\0':
+                break;
+            default:
+                if (NM_IN_SET(*p, ',', ';'))
+                    *q = *p;
+                else {
+                    *q++ = '\\';
+                    *q   = *p;
+                }
+                break;
+            }
+            if (*p == '\0')
+                break;
+            p++;
+            trailing_ws = 0;
+        } else {
+            *q = *p;
+            if (*p == '\0')
+                break;
+            if (g_ascii_isspace(*p)) {
+                trailing_ws++;
+                p++;
+            } else if (NM_IN_SET(*p, ',', ';')) {
+                if (q0 < q - trailing_ws)
+                    pieces = g_slist_prepend(pieces, g_strndup(q0, (q - q0) - trailing_ws));
+                q0 = q + 1;
+                p++;
+                trailing_ws = 0;
+                while (g_ascii_isspace(*p))
+                    p++;
+            } else
+                p++;
+        }
+        q++;
+    }
+
+    *q = '\0';
+    if (q0 < q - trailing_ws)
+        pieces = g_slist_prepend(pieces, g_strndup(q0, (q - q0) - trailing_ws));
+    g_free(string_value);
+    return g_slist_reverse(pieces);
 }
 
 /**
@@ -1633,258 +1837,253 @@ nm_match_spec_split (const char *value)
  *   ways to encode the same joined specs string).
  */
 char *
-nm_match_spec_join (GSList *specs)
+nm_match_spec_join(GSList *specs)
 {
-	const char *p;
-	GString *str;
-
-	str = g_string_new ("");
-
-	for (; specs; specs = specs->next) {
-		p = specs->data;
-
-		if (!p || !*p)
-			continue;
-
-		if (str->len > 0)
-			g_string_append_c (str, ',');
-
-		/* escape leading whitespace */
-		switch (*p) {
-		case ' ':
-			g_string_append (str, "\\s");
-			p++;
-			break;
-		case '\t':
-			g_string_append (str, "\\t");
-			p++;
-			break;
-		}
-
-		for (; *p; p++) {
-			switch (*p) {
-			case '\n':
-				g_string_append (str, "\\n");
-				break;
-			case '\r':
-				g_string_append (str, "\\r");
-				break;
-			case '\\':
-				g_string_append (str, "\\\\");
-				break;
-			case ',':
-				g_string_append (str, "\\,");
-				break;
-			case ';':
-				g_string_append (str, "\\;");
-				break;
-			default:
-				g_string_append_c (str, *p);
-				break;
-			}
-		}
-
-		/* escape trailing whitespaces */
-		switch (str->str[str->len - 1]) {
-		case ' ':
-			g_string_overwrite (str, str->len - 1, "\\s");
-			break;
-		case '\t':
-			g_string_overwrite (str, str->len - 1, "\\t");
-			break;
-		}
-	}
-
-	return g_string_free (str, FALSE);
+    const char *p;
+    GString *   str;
+
+    str = g_string_new("");
+
+    for (; specs; specs = specs->next) {
+        p = specs->data;
+
+        if (!p || !*p)
+            continue;
+
+        if (str->len > 0)
+            g_string_append_c(str, ',');
+
+        /* escape leading whitespace */
+        switch (*p) {
+        case ' ':
+            g_string_append(str, "\\s");
+            p++;
+            break;
+        case '\t':
+            g_string_append(str, "\\t");
+            p++;
+            break;
+        }
+
+        for (; *p; p++) {
+            switch (*p) {
+            case '\n':
+                g_string_append(str, "\\n");
+                break;
+            case '\r':
+                g_string_append(str, "\\r");
+                break;
+            case '\\':
+                g_string_append(str, "\\\\");
+                break;
+            case ',':
+                g_string_append(str, "\\,");
+                break;
+            case ';':
+                g_string_append(str, "\\;");
+                break;
+            default:
+                g_string_append_c(str, *p);
+                break;
+            }
+        }
+
+        /* escape trailing whitespaces */
+        switch (str->str[str->len - 1]) {
+        case ' ':
+            g_string_overwrite(str, str->len - 1, "\\s");
+            break;
+        case '\t':
+            g_string_overwrite(str, str->len - 1, "\\t");
+            break;
+        }
+    }
+
+    return g_string_free(str, FALSE);
 }
 
 static void
-_pattern_parse (const char *input,
-                const char **out_pattern,
-                gboolean *out_is_inverted,
-                gboolean *out_is_mandatory)
+_pattern_parse(const char * input,
+               const char **out_pattern,
+               gboolean *   out_is_inverted,
+               gboolean *   out_is_mandatory)
 {
-	gboolean is_inverted = FALSE;
-	gboolean is_mandatory = FALSE;
-
-	if (input[0] == '&') {
-		input++;
-		is_mandatory = TRUE;
-		if (input[0] == '!') {
-			input++;
-			is_inverted = TRUE;
-		}
-		goto out;
-	}
-
-	if (input[0] == '|') {
-		input++;
-		if (input[0] == '!') {
-			input++;
-			is_inverted = TRUE;
-		}
-		goto out;
-	}
-
-	if (input[0] == '!') {
-		input++;
-		is_inverted = TRUE;
-		is_mandatory = TRUE;
-		goto out;
-	}
+    gboolean is_inverted  = FALSE;
+    gboolean is_mandatory = FALSE;
+
+    if (input[0] == '&') {
+        input++;
+        is_mandatory = TRUE;
+        if (input[0] == '!') {
+            input++;
+            is_inverted = TRUE;
+        }
+        goto out;
+    }
+
+    if (input[0] == '|') {
+        input++;
+        if (input[0] == '!') {
+            input++;
+            is_inverted = TRUE;
+        }
+        goto out;
+    }
+
+    if (input[0] == '!') {
+        input++;
+        is_inverted  = TRUE;
+        is_mandatory = TRUE;
+        goto out;
+    }
 
 out:
-	if (input[0] == '\\')
-		input++;
+    if (input[0] == '\\')
+        input++;
 
-	*out_pattern = input;
-	*out_is_inverted = is_inverted;
-	*out_is_mandatory = is_mandatory;
+    *out_pattern      = input;
+    *out_is_inverted  = is_inverted;
+    *out_is_mandatory = is_mandatory;
 }
 
 gboolean
-nm_wildcard_match_check (const char *str,
-                         const char *const *patterns,
-                         guint num_patterns)
+nm_wildcard_match_check(const char *str, const char *const *patterns, guint num_patterns)
 {
-	gboolean has_optional = FALSE;
-	gboolean has_any_optional = FALSE;
-	guint i;
-
-	for (i = 0; i < num_patterns; i++) {
-		gboolean is_inverted;
-		gboolean is_mandatory;
-		gboolean match;
-		const char *p;
-
-		_pattern_parse (patterns[i], &p, &is_inverted, &is_mandatory);
-
-		match = (fnmatch (p, str, 0) == 0);
-		if (is_inverted)
-			match = !match;
-
-		if (is_mandatory) {
-			if (!match)
-				return FALSE;
-		} else {
-			has_any_optional = TRUE;
-			if (match)
-				has_optional = TRUE;
-		}
-	}
-
-	return    has_optional
-	       || !has_any_optional;
+    gboolean has_optional     = FALSE;
+    gboolean has_any_optional = FALSE;
+    guint    i;
+
+    for (i = 0; i < num_patterns; i++) {
+        gboolean    is_inverted;
+        gboolean    is_mandatory;
+        gboolean    match;
+        const char *p;
+
+        _pattern_parse(patterns[i], &p, &is_inverted, &is_mandatory);
+
+        match = (fnmatch(p, str, 0) == 0);
+        if (is_inverted)
+            match = !match;
+
+        if (is_mandatory) {
+            if (!match)
+                return FALSE;
+        } else {
+            has_any_optional = TRUE;
+            if (match)
+                has_optional = TRUE;
+        }
+    }
+
+    return has_optional || !has_any_optional;
 }
 
 /*****************************************************************************/
 
 static gboolean
-_kernel_cmdline_match (const char *const*proc_cmdline,
-                       const char *pattern)
+_kernel_cmdline_match(const char *const *proc_cmdline, const char *pattern)
 {
-
-	if (proc_cmdline) {
-		gboolean has_equal = (!!strchr (pattern, '='));
-		gsize pattern_len = strlen (pattern);
-
-		for (; proc_cmdline[0]; proc_cmdline++) {
-			const char *c = proc_cmdline[0];
-
-			if (has_equal) {
-				/* if pattern contains '=' compare full key=value */
-				if (nm_streq (c, pattern))
-					return TRUE;
-				continue;
-			}
-
-			/* otherwise consider pattern as key only */
-			if (   strncmp (c, pattern, pattern_len) == 0
-			    && NM_IN_SET (c[pattern_len], '\0', '='))
-				return TRUE;
-		}
-	}
-
-	return FALSE;
+    if (proc_cmdline) {
+        gboolean has_equal   = (!!strchr(pattern, '='));
+        gsize    pattern_len = strlen(pattern);
+
+        for (; proc_cmdline[0]; proc_cmdline++) {
+            const char *c = proc_cmdline[0];
+
+            if (has_equal) {
+                /* if pattern contains '=' compare full key=value */
+                if (nm_streq(c, pattern))
+                    return TRUE;
+                continue;
+            }
+
+            /* otherwise consider pattern as key only */
+            if (strncmp(c, pattern, pattern_len) == 0 && NM_IN_SET(c[pattern_len], '\0', '='))
+                return TRUE;
+        }
+    }
+
+    return FALSE;
 }
 
 gboolean
-nm_utils_kernel_cmdline_match_check (const char *const*proc_cmdline,
-                                     const char *const*patterns,
-                                     guint num_patterns,
-                                     GError **error)
+nm_utils_kernel_cmdline_match_check(const char *const *proc_cmdline,
+                                    const char *const *patterns,
+                                    guint              num_patterns,
+                                    GError **          error)
 {
-	gboolean has_optional = FALSE;
-	gboolean has_any_optional = FALSE;
-	guint i;
-
-	for (i = 0; i < num_patterns; i++) {
-		const char *element = patterns[i];
-		gboolean is_inverted = FALSE;
-		gboolean is_mandatory = FALSE;
-		gboolean match;
-		const char *p;
-
-		_pattern_parse (element, &p, &is_inverted, &is_mandatory);
-
-		match = _kernel_cmdline_match (proc_cmdline, p);
-		if (is_inverted)
-			match = !match;
-
-		if (is_mandatory) {
-			if (!match) {
-				nm_utils_error_set (error, NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
-				                    "device does not satisfy match.kernel-command-line property %s",
-				                    patterns[i]);
-				return FALSE;
-			}
-		} else {
-			has_any_optional = TRUE;
-			if (match)
-				has_optional = TRUE;
-		}
-	}
-
-	if (   !has_optional
-	    && has_any_optional) {
-		nm_utils_error_set (error, NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
-		                    "device does not satisfy any match.kernel-command-line property");
-		return FALSE;
-	}
-
-	return TRUE;
+    gboolean has_optional     = FALSE;
+    gboolean has_any_optional = FALSE;
+    guint    i;
+
+    for (i = 0; i < num_patterns; i++) {
+        const char *element      = patterns[i];
+        gboolean    is_inverted  = FALSE;
+        gboolean    is_mandatory = FALSE;
+        gboolean    match;
+        const char *p;
+
+        _pattern_parse(element, &p, &is_inverted, &is_mandatory);
+
+        match = _kernel_cmdline_match(proc_cmdline, p);
+        if (is_inverted)
+            match = !match;
+
+        if (is_mandatory) {
+            if (!match) {
+                nm_utils_error_set(error,
+                                   NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
+                                   "device does not satisfy match.kernel-command-line property %s",
+                                   patterns[i]);
+                return FALSE;
+            }
+        } else {
+            has_any_optional = TRUE;
+            if (match)
+                has_optional = TRUE;
+        }
+    }
+
+    if (!has_optional && has_any_optional) {
+        nm_utils_error_set(error,
+                           NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
+                           "device does not satisfy any match.kernel-command-line property");
+        return FALSE;
+    }
+
+    return TRUE;
 }
 
 /*****************************************************************************/
 
 char *
-nm_utils_new_vlan_name (const char *parent_iface, guint32 vlan_id)
+nm_utils_new_vlan_name(const char *parent_iface, guint32 vlan_id)
 {
-	guint id_len;
-	gsize parent_len;
-	char *ifname;
-
-	g_return_val_if_fail (parent_iface && *parent_iface, NULL);
-
-	if (vlan_id < 10)
-		id_len = 2;
-	else if (vlan_id < 100)
-		id_len = 3;
-	else if (vlan_id < 1000)
-		id_len = 4;
-	else {
-		g_return_val_if_fail (vlan_id < 4095, NULL);
-		id_len = 5;
-	}
-
-	ifname = g_new (char, IFNAMSIZ);
-
-	parent_len = strlen (parent_iface);
-	parent_len = MIN (parent_len, IFNAMSIZ - 1 - id_len);
-	memcpy (ifname, parent_iface, parent_len);
-	g_snprintf (&ifname[parent_len], IFNAMSIZ - parent_len, ".%u", vlan_id);
-
-	return ifname;
+    guint id_len;
+    gsize parent_len;
+    char *ifname;
+
+    g_return_val_if_fail(parent_iface && *parent_iface, NULL);
+
+    if (vlan_id < 10)
+        id_len = 2;
+    else if (vlan_id < 100)
+        id_len = 3;
+    else if (vlan_id < 1000)
+        id_len = 4;
+    else {
+        g_return_val_if_fail(vlan_id < 4095, NULL);
+        id_len = 5;
+    }
+
+    ifname = g_new(char, IFNAMSIZ);
+
+    parent_len = strlen(parent_iface);
+    parent_len = MIN(parent_len, IFNAMSIZ - 1 - id_len);
+    memcpy(ifname, parent_iface, parent_len);
+    g_snprintf(&ifname[parent_len], IFNAMSIZ - parent_len, ".%u", vlan_id);
+
+    return ifname;
 }
 
 /* nm_utils_new_infiniband_name:
@@ -1897,21 +2096,21 @@ nm_utils_new_vlan_name (const char *parent_iface, guint32 vlan_id)
  *   is returned.
  */
 const char *
-nm_utils_new_infiniband_name (char *name, const char *parent_name, int p_key)
+nm_utils_new_infiniband_name(char *name, const char *parent_name, int p_key)
 {
-	g_return_val_if_fail (name, NULL);
-	g_return_val_if_fail (parent_name && parent_name[0], NULL);
-	g_return_val_if_fail (strlen (parent_name) < IFNAMSIZ, NULL);
-
-	/* technically, p_key of 0x0000 and 0x8000 is not allowed either. But we don't
-	 * want to assert against that in nm_utils_new_infiniband_name(). So be more
-	 * resilient here, and accept those. */
-	g_return_val_if_fail (p_key >= 0 && p_key <= 0xffff, NULL);
-
-	/* If parent+suffix is too long, kernel would just truncate
-	 * the name. We do the same. See ipoib_vlan_add().  */
-	g_snprintf (name, IFNAMSIZ, "%s.%04x", parent_name, p_key);
-	return name;
+    g_return_val_if_fail(name, NULL);
+    g_return_val_if_fail(parent_name && parent_name[0], NULL);
+    g_return_val_if_fail(strlen(parent_name) < IFNAMSIZ, NULL);
+
+    /* technically, p_key of 0x0000 and 0x8000 is not allowed either. But we don't
+     * want to assert against that in nm_utils_new_infiniband_name(). So be more
+     * resilient here, and accept those. */
+    g_return_val_if_fail(p_key >= 0 && p_key <= 0xffff, NULL);
+
+    /* If parent+suffix is too long, kernel would just truncate
+     * the name. We do the same. See ipoib_vlan_add().  */
+    g_snprintf(name, IFNAMSIZ, "%s.%04x", parent_name, p_key);
+    return name;
 }
 
 /*****************************************************************************/
@@ -1933,327 +2132,422 @@ nm_utils_new_infiniband_name (char *name, const char *parent_name, int p_key)
  * Returns: -1, 0, or 1
  */
 int
-nm_utils_cmp_connection_by_autoconnect_priority (NMConnection *a, NMConnection *b)
+nm_utils_cmp_connection_by_autoconnect_priority(NMConnection *a, NMConnection *b)
 {
-	NMSettingConnection *a_s_con;
-	NMSettingConnection *b_s_con;
-	int a_ap, b_ap;
-	gboolean can_autoconnect;
-
-	if (a == b)
-		return 0;
-	if (!a)
-		return 1;
-	if (!b)
-		return -1;
-
-	a_s_con = nm_connection_get_setting_connection (a);
-	b_s_con = nm_connection_get_setting_connection (b);
-
-	if (!a_s_con)
-		return !b_s_con ? 0 : 1;
-	if (!b_s_con)
-		return -1;
-
-	can_autoconnect = !!nm_setting_connection_get_autoconnect (a_s_con);
-	if (can_autoconnect != (!!nm_setting_connection_get_autoconnect (b_s_con)))
-		return can_autoconnect ? -1 : 1;
-
-	if (can_autoconnect) {
-		a_ap = nm_setting_connection_get_autoconnect_priority (a_s_con);
-		b_ap = nm_setting_connection_get_autoconnect_priority (b_s_con);
-		if (a_ap != b_ap)
-			return (a_ap > b_ap) ? -1 : 1;
-	}
-
-	return 0;
+    NMSettingConnection *a_s_con;
+    NMSettingConnection *b_s_con;
+    int                  a_ap, b_ap;
+    gboolean             can_autoconnect;
+
+    if (a == b)
+        return 0;
+    if (!a)
+        return 1;
+    if (!b)
+        return -1;
+
+    a_s_con = nm_connection_get_setting_connection(a);
+    b_s_con = nm_connection_get_setting_connection(b);
+
+    if (!a_s_con)
+        return !b_s_con ? 0 : 1;
+    if (!b_s_con)
+        return -1;
+
+    can_autoconnect = !!nm_setting_connection_get_autoconnect(a_s_con);
+    if (can_autoconnect != (!!nm_setting_connection_get_autoconnect(b_s_con)))
+        return can_autoconnect ? -1 : 1;
+
+    if (can_autoconnect) {
+        a_ap = nm_setting_connection_get_autoconnect_priority(a_s_con);
+        b_ap = nm_setting_connection_get_autoconnect_priority(b_s_con);
+        if (a_ap != b_ap)
+            return (a_ap > b_ap) ? -1 : 1;
+    }
+
+    return 0;
 }
 
 /*****************************************************************************/
 
-typedef struct
-{
-	const char *name;
-	NMSetting *setting;
-	NMSetting *diff_base_setting;
-	GHashTable *setting_diff;
+typedef struct {
+    const char *name;
+    NMSetting * setting;
+    NMSetting * diff_base_setting;
+    GHashTable *setting_diff;
 } LogConnectionSettingData;
 
-typedef struct
-{
-	const char *item_name;
-	NMSettingDiffResult diff_result;
+typedef struct {
+    const char *        item_name;
+    NMSettingDiffResult diff_result;
 } LogConnectionSettingItem;
 
 static int
-_log_connection_sort_hashes_fcn (gconstpointer a, gconstpointer b)
+_log_connection_sort_hashes_fcn(gconstpointer a, gconstpointer b)
 {
-	const LogConnectionSettingData *v1 = a;
-	const LogConnectionSettingData *v2 = b;
-	NMSettingPriority p1, p2;
-	NMSetting *s1, *s2;
+    const LogConnectionSettingData *v1 = a;
+    const LogConnectionSettingData *v2 = b;
+    NMSettingPriority               p1, p2;
+    NMSetting *                     s1, *s2;
 
-	s1 = v1->setting ?: v1->diff_base_setting;
-	s2 = v2->setting ?: v2->diff_base_setting;
+    s1 = v1->setting ?: v1->diff_base_setting;
+    s2 = v2->setting ?: v2->diff_base_setting;
 
-	g_assert (s1 && s2);
+    g_assert(s1 && s2);
 
-	p1 = _nm_setting_get_setting_priority (s1);
-	p2 = _nm_setting_get_setting_priority (s2);
+    p1 = _nm_setting_get_setting_priority(s1);
+    p2 = _nm_setting_get_setting_priority(s2);
 
-	if (p1 != p2)
-		return p1 > p2 ? 1 : -1;
+    if (p1 != p2)
+        return p1 > p2 ? 1 : -1;
 
-	return strcmp (v1->name, v2->name);
+    return strcmp(v1->name, v2->name);
 }
 
 static GArray *
-_log_connection_sort_hashes (NMConnection *connection, NMConnection *diff_base, GHashTable *connection_diff)
+_log_connection_sort_hashes(NMConnection *connection,
+                            NMConnection *diff_base,
+                            GHashTable *  connection_diff)
 {
-	GHashTableIter iter;
-	GArray *sorted_hashes;
-	LogConnectionSettingData setting_data;
-
-	sorted_hashes = g_array_sized_new (TRUE, FALSE, sizeof (LogConnectionSettingData), g_hash_table_size (connection_diff));
-
-	g_hash_table_iter_init (&iter, connection_diff);
-	while (g_hash_table_iter_next (&iter, (gpointer) &setting_data.name, (gpointer) &setting_data.setting_diff)) {
-		setting_data.setting = nm_connection_get_setting_by_name (connection, setting_data.name);
-		setting_data.diff_base_setting = diff_base ? nm_connection_get_setting_by_name (diff_base, setting_data.name) : NULL;
-		g_assert (setting_data.setting || setting_data.diff_base_setting);
-		g_array_append_val (sorted_hashes, setting_data);
-	}
-
-	g_array_sort (sorted_hashes, _log_connection_sort_hashes_fcn);
-	return sorted_hashes;
+    GHashTableIter           iter;
+    GArray *                 sorted_hashes;
+    LogConnectionSettingData setting_data;
+
+    sorted_hashes = g_array_sized_new(TRUE,
+                                      FALSE,
+                                      sizeof(LogConnectionSettingData),
+                                      g_hash_table_size(connection_diff));
+
+    g_hash_table_iter_init(&iter, connection_diff);
+    while (g_hash_table_iter_next(&iter,
+                                  (gpointer) &setting_data.name,
+                                  (gpointer) &setting_data.setting_diff)) {
+        setting_data.setting = nm_connection_get_setting_by_name(connection, setting_data.name);
+        setting_data.diff_base_setting =
+            diff_base ? nm_connection_get_setting_by_name(diff_base, setting_data.name) : NULL;
+        g_assert(setting_data.setting || setting_data.diff_base_setting);
+        g_array_append_val(sorted_hashes, setting_data);
+    }
+
+    g_array_sort(sorted_hashes, _log_connection_sort_hashes_fcn);
+    return sorted_hashes;
 }
 
 static int
-_log_connection_sort_names_fcn (gconstpointer a, gconstpointer b)
+_log_connection_sort_names_fcn(gconstpointer a, gconstpointer b)
 {
-	const LogConnectionSettingItem *v1 = a;
-	const LogConnectionSettingItem *v2 = b;
-
-	/* we want to first show the items, that disappeared, then the one that changed and
-	 * then the ones that were added. */
-
-	if ((v1->diff_result & NM_SETTING_DIFF_RESULT_IN_A) != (v2->diff_result & NM_SETTING_DIFF_RESULT_IN_A))
-		return (v1->diff_result & NM_SETTING_DIFF_RESULT_IN_A) ? -1 : 1;
-	if ((v1->diff_result & NM_SETTING_DIFF_RESULT_IN_B) != (v2->diff_result & NM_SETTING_DIFF_RESULT_IN_B))
-		return (v1->diff_result & NM_SETTING_DIFF_RESULT_IN_B) ? 1 : -1;
-	return strcmp (v1->item_name, v2->item_name);
+    const LogConnectionSettingItem *v1 = a;
+    const LogConnectionSettingItem *v2 = b;
+
+    /* we want to first show the items, that disappeared, then the one that changed and
+     * then the ones that were added. */
+
+    if ((v1->diff_result & NM_SETTING_DIFF_RESULT_IN_A)
+        != (v2->diff_result & NM_SETTING_DIFF_RESULT_IN_A))
+        return (v1->diff_result & NM_SETTING_DIFF_RESULT_IN_A) ? -1 : 1;
+    if ((v1->diff_result & NM_SETTING_DIFF_RESULT_IN_B)
+        != (v2->diff_result & NM_SETTING_DIFF_RESULT_IN_B))
+        return (v1->diff_result & NM_SETTING_DIFF_RESULT_IN_B) ? 1 : -1;
+    return strcmp(v1->item_name, v2->item_name);
 }
 
 static char *
-_log_connection_get_property (NMSetting *setting, const char *name)
+_log_connection_get_property(NMSetting *setting, const char *name)
 {
-	GValue val = G_VALUE_INIT;
-	char *s;
-
-	g_return_val_if_fail (setting, NULL);
-
-	if (   !NM_IS_SETTING_VPN (setting)
-	    && nm_setting_get_secret_flags (setting, name, NULL, NULL))
-		return g_strdup ("****");
-
-	if (!_nm_setting_get_property (setting, name, &val))
-		return g_strdup ("<unknown>");
-
-	if (G_VALUE_HOLDS_STRING (&val)) {
-		const char *val_s;
-
-		val_s = g_value_get_string (&val);
-		if (!val_s) {
-			/* for NULL, we want to return the unquoted string "NULL". */
-			s = g_strdup ("NULL");
-		} else {
-			char *escaped = g_strescape (val_s, "'");
-
-			s = g_strdup_printf ("'%s'", escaped);
-			g_free (escaped);
-		}
-	} else {
-		s = g_strdup_value_contents (&val);
-		if (s == NULL)
-			s = g_strdup ("NULL");
-		else {
-			char *escaped = g_strescape (s, "'");
-
-			g_free (s);
-			s = escaped;
-		}
-	}
-	g_value_unset(&val);
-	return s;
+    GValue val = G_VALUE_INIT;
+    char * s;
+
+    g_return_val_if_fail(setting, NULL);
+
+    if (!NM_IS_SETTING_VPN(setting) && nm_setting_get_secret_flags(setting, name, NULL, NULL))
+        return g_strdup("****");
+
+    if (!_nm_setting_get_property(setting, name, &val))
+        return g_strdup("<unknown>");
+
+    if (G_VALUE_HOLDS_STRING(&val)) {
+        const char *val_s;
+
+        val_s = g_value_get_string(&val);
+        if (!val_s) {
+            /* for NULL, we want to return the unquoted string "NULL". */
+            s = g_strdup("NULL");
+        } else {
+            char *escaped = g_strescape(val_s, "'");
+
+            s = g_strdup_printf("'%s'", escaped);
+            g_free(escaped);
+        }
+    } else {
+        s = g_strdup_value_contents(&val);
+        if (s == NULL)
+            s = g_strdup("NULL");
+        else {
+            char *escaped = g_strescape(s, "'");
+
+            g_free(s);
+            s = escaped;
+        }
+    }
+    g_value_unset(&val);
+    return s;
 }
 
 static void
-_log_connection_sort_names (LogConnectionSettingData *setting_data, GArray *sorted_names)
+_log_connection_sort_names(LogConnectionSettingData *setting_data, GArray *sorted_names)
 {
-	GHashTableIter iter;
-	LogConnectionSettingItem item;
-	gpointer p;
+    GHashTableIter           iter;
+    LogConnectionSettingItem item;
+    gpointer                 p;
 
-	g_array_set_size (sorted_names, 0);
+    g_array_set_size(sorted_names, 0);
 
-	g_hash_table_iter_init (&iter, setting_data->setting_diff);
-	while (g_hash_table_iter_next (&iter, (gpointer) &item.item_name, &p)) {
-		item.diff_result = GPOINTER_TO_UINT (p);
-		g_array_append_val (sorted_names, item);
-	}
+    g_hash_table_iter_init(&iter, setting_data->setting_diff);
+    while (g_hash_table_iter_next(&iter, (gpointer) &item.item_name, &p)) {
+        item.diff_result = GPOINTER_TO_UINT(p);
+        g_array_append_val(sorted_names, item);
+    }
 
-	g_array_sort (sorted_names, _log_connection_sort_names_fcn);
+    g_array_sort(sorted_names, _log_connection_sort_names_fcn);
 }
 
 void
-nm_utils_log_connection_diff (NMConnection *connection,
-                              NMConnection *diff_base,
-                              guint32 level,
-                              guint64 domain,
-                              const char *name,
-                              const char *prefix,
-                              const char *dbus_path)
+nm_utils_log_connection_diff(NMConnection *connection,
+                             NMConnection *diff_base,
+                             guint32       level,
+                             guint64       domain,
+                             const char *  name,
+                             const char *  prefix,
+                             const char *  dbus_path)
 {
-	GHashTable *connection_diff = NULL;
-	GArray *sorted_hashes;
-	GArray *sorted_names = NULL;
-	int i, j;
-	gboolean connection_diff_are_same;
-	gboolean print_header = TRUE;
-	gboolean print_setting_header;
-	GString *str1;
-
-	g_return_if_fail (NM_IS_CONNECTION (connection));
-	g_return_if_fail (!diff_base || (NM_IS_CONNECTION (diff_base) && diff_base != connection));
-
-	/* For VPN setting types, this is broken, because we cannot (generically) print the content of data/secrets. Bummer... */
-
-	if (!nm_logging_enabled (level, domain))
-		return;
-
-	if (!prefix)
-		prefix = "";
-	if (!name)
-		name = "";
-
-	connection_diff_are_same = nm_connection_diff (connection, diff_base,
-	                                               NM_SETTING_COMPARE_FLAG_EXACT | NM_SETTING_COMPARE_FLAG_DIFF_RESULT_NO_DEFAULT,
-	                                               &connection_diff);
-	if (connection_diff_are_same) {
-		const char *t1, *t2;
-
-		t1 = nm_connection_get_connection_type (connection);
-		if (diff_base) {
-			t2 = nm_connection_get_connection_type (diff_base);
-			nm_log (level, domain, NULL, NULL,
-			        "%sconnection '%s' (%p/%s/%s%s%s and %p/%s/%s%s%s): no difference",
-			        prefix, name,
-			        connection, G_OBJECT_TYPE_NAME (connection), NM_PRINT_FMT_QUOTE_STRING (t1),
-			        diff_base, G_OBJECT_TYPE_NAME (diff_base), NM_PRINT_FMT_QUOTE_STRING (t2));
-		} else {
-			nm_log (level, domain, NULL, NULL,
-			        "%sconnection '%s' (%p/%s/%s%s%s): no properties set",
-			        prefix, name,
-			        connection, G_OBJECT_TYPE_NAME (connection), NM_PRINT_FMT_QUOTE_STRING (t1));
-		}
-		g_assert (!connection_diff);
-		return;
-	}
-
-	/* FIXME: it doesn't nicely show the content of NMSettingVpn, because nm_connection_diff() does not
-	 * expand the hash values. */
-
-	sorted_hashes = _log_connection_sort_hashes (connection, diff_base, connection_diff);
-	if (sorted_hashes->len <= 0)
-		goto out;
-
-	sorted_names = g_array_new (FALSE, FALSE, sizeof (LogConnectionSettingItem));
-	str1 = g_string_new (NULL);
-
-	for (i = 0; i < sorted_hashes->len; i++) {
-		LogConnectionSettingData *setting_data = &g_array_index (sorted_hashes, LogConnectionSettingData, i);
-
-		_log_connection_sort_names (setting_data, sorted_names);
-		print_setting_header = TRUE;
-		for (j = 0; j < sorted_names->len; j++) {
-			char *str_conn, *str_diff;
-			LogConnectionSettingItem *item = &g_array_index (sorted_names, LogConnectionSettingItem, j);
-
-			str_conn = (item->diff_result & NM_SETTING_DIFF_RESULT_IN_A)
-			           ? _log_connection_get_property (setting_data->setting, item->item_name)
-			           : NULL;
-			str_diff = (item->diff_result & NM_SETTING_DIFF_RESULT_IN_B)
-			           ? _log_connection_get_property (setting_data->diff_base_setting, item->item_name)
-			           : NULL;
-
-			if (print_header) {
-				GError *err_verify = NULL;
-				const char *t1, *t2;
-
-				t1 = nm_connection_get_connection_type (connection);
-				if (diff_base) {
-					t2 = nm_connection_get_connection_type (diff_base);
-					nm_log (level, domain, NULL, NULL, "%sconnection '%s' (%p/%s/%s%s%s < %p/%s/%s%s%s)%s%s%s:",
-					        prefix, name,
-					        connection, G_OBJECT_TYPE_NAME (connection), NM_PRINT_FMT_QUOTE_STRING (t1),
-					        diff_base, G_OBJECT_TYPE_NAME (diff_base), NM_PRINT_FMT_QUOTE_STRING (t2),
-					        NM_PRINT_FMT_QUOTED (dbus_path, " [", dbus_path, "]", ""));
-				} else {
-					nm_log (level, domain, NULL, NULL, "%sconnection '%s' (%p/%s/%s%s%s):%s%s%s",
-					        prefix, name,
-					        connection, G_OBJECT_TYPE_NAME (connection), NM_PRINT_FMT_QUOTE_STRING (t1),
-					        NM_PRINT_FMT_QUOTED (dbus_path, " [", dbus_path, "]", ""));
-				}
-				print_header = FALSE;
-
-				if (!nm_connection_verify (connection, &err_verify)) {
-					nm_log (level, domain, NULL, NULL, "%sconnection %p does not verify: %s", prefix, connection, err_verify->message);
-					g_clear_error (&err_verify);
-				}
-			}
+    GHashTable *connection_diff = NULL;
+    GArray *    sorted_hashes;
+    GArray *    sorted_names = NULL;
+    int         i, j;
+    gboolean    connection_diff_are_same;
+    gboolean    print_header = TRUE;
+    gboolean    print_setting_header;
+    GString *   str1;
+
+    g_return_if_fail(NM_IS_CONNECTION(connection));
+    g_return_if_fail(!diff_base || (NM_IS_CONNECTION(diff_base) && diff_base != connection));
+
+    /* For VPN setting types, this is broken, because we cannot (generically) print the content of data/secrets. Bummer... */
+
+    if (!nm_logging_enabled(level, domain))
+        return;
+
+    if (!prefix)
+        prefix = "";
+    if (!name)
+        name = "";
+
+    connection_diff_are_same = nm_connection_diff(
+        connection,
+        diff_base,
+        NM_SETTING_COMPARE_FLAG_EXACT | NM_SETTING_COMPARE_FLAG_DIFF_RESULT_NO_DEFAULT,
+        &connection_diff);
+    if (connection_diff_are_same) {
+        const char *t1, *t2;
+
+        t1 = nm_connection_get_connection_type(connection);
+        if (diff_base) {
+            t2 = nm_connection_get_connection_type(diff_base);
+            nm_log(level,
+                   domain,
+                   NULL,
+                   NULL,
+                   "%sconnection '%s' (%p/%s/%s%s%s and %p/%s/%s%s%s): no difference",
+                   prefix,
+                   name,
+                   connection,
+                   G_OBJECT_TYPE_NAME(connection),
+                   NM_PRINT_FMT_QUOTE_STRING(t1),
+                   diff_base,
+                   G_OBJECT_TYPE_NAME(diff_base),
+                   NM_PRINT_FMT_QUOTE_STRING(t2));
+        } else {
+            nm_log(level,
+                   domain,
+                   NULL,
+                   NULL,
+                   "%sconnection '%s' (%p/%s/%s%s%s): no properties set",
+                   prefix,
+                   name,
+                   connection,
+                   G_OBJECT_TYPE_NAME(connection),
+                   NM_PRINT_FMT_QUOTE_STRING(t1));
+        }
+        g_assert(!connection_diff);
+        return;
+    }
+
+    /* FIXME: it doesn't nicely show the content of NMSettingVpn, because nm_connection_diff() does not
+     * expand the hash values. */
+
+    sorted_hashes = _log_connection_sort_hashes(connection, diff_base, connection_diff);
+    if (sorted_hashes->len <= 0)
+        goto out;
+
+    sorted_names = g_array_new(FALSE, FALSE, sizeof(LogConnectionSettingItem));
+    str1         = g_string_new(NULL);
+
+    for (i = 0; i < sorted_hashes->len; i++) {
+        LogConnectionSettingData *setting_data =
+            &g_array_index(sorted_hashes, LogConnectionSettingData, i);
+
+        _log_connection_sort_names(setting_data, sorted_names);
+        print_setting_header = TRUE;
+        for (j = 0; j < sorted_names->len; j++) {
+            char *                    str_conn, *str_diff;
+            LogConnectionSettingItem *item =
+                &g_array_index(sorted_names, LogConnectionSettingItem, j);
+
+            str_conn = (item->diff_result & NM_SETTING_DIFF_RESULT_IN_A)
+                           ? _log_connection_get_property(setting_data->setting, item->item_name)
+                           : NULL;
+            str_diff =
+                (item->diff_result & NM_SETTING_DIFF_RESULT_IN_B)
+                    ? _log_connection_get_property(setting_data->diff_base_setting, item->item_name)
+                    : NULL;
+
+            if (print_header) {
+                GError *    err_verify = NULL;
+                const char *t1, *t2;
+
+                t1 = nm_connection_get_connection_type(connection);
+                if (diff_base) {
+                    t2 = nm_connection_get_connection_type(diff_base);
+                    nm_log(level,
+                           domain,
+                           NULL,
+                           NULL,
+                           "%sconnection '%s' (%p/%s/%s%s%s < %p/%s/%s%s%s)%s%s%s:",
+                           prefix,
+                           name,
+                           connection,
+                           G_OBJECT_TYPE_NAME(connection),
+                           NM_PRINT_FMT_QUOTE_STRING(t1),
+                           diff_base,
+                           G_OBJECT_TYPE_NAME(diff_base),
+                           NM_PRINT_FMT_QUOTE_STRING(t2),
+                           NM_PRINT_FMT_QUOTED(dbus_path, " [", dbus_path, "]", ""));
+                } else {
+                    nm_log(level,
+                           domain,
+                           NULL,
+                           NULL,
+                           "%sconnection '%s' (%p/%s/%s%s%s):%s%s%s",
+                           prefix,
+                           name,
+                           connection,
+                           G_OBJECT_TYPE_NAME(connection),
+                           NM_PRINT_FMT_QUOTE_STRING(t1),
+                           NM_PRINT_FMT_QUOTED(dbus_path, " [", dbus_path, "]", ""));
+                }
+                print_header = FALSE;
+
+                if (!nm_connection_verify(connection, &err_verify)) {
+                    nm_log(level,
+                           domain,
+                           NULL,
+                           NULL,
+                           "%sconnection %p does not verify: %s",
+                           prefix,
+                           connection,
+                           err_verify->message);
+                    g_clear_error(&err_verify);
+                }
+            }
 #define _NM_LOG_ALIGN "-25"
-			if (print_setting_header) {
-				if (diff_base) {
-					if (setting_data->setting && setting_data->diff_base_setting)
-						g_string_printf (str1, "%p < %p", setting_data->setting, setting_data->diff_base_setting);
-					else if (setting_data->diff_base_setting)
-						g_string_printf (str1, "*missing* < %p", setting_data->diff_base_setting);
-					else
-						g_string_printf (str1, "%p < *missing*", setting_data->setting);
-					nm_log (level, domain, NULL, NULL, "%s%"_NM_LOG_ALIGN"s [ %s ]", prefix, setting_data->name, str1->str);
-				} else
-					nm_log (level, domain, NULL, NULL, "%s%"_NM_LOG_ALIGN"s [ %p ]", prefix, setting_data->name, setting_data->setting);
-				print_setting_header = FALSE;
-			}
-			g_string_printf (str1, "%s.%s", setting_data->name, item->item_name);
-			switch (item->diff_result & (NM_SETTING_DIFF_RESULT_IN_A | NM_SETTING_DIFF_RESULT_IN_B)) {
-				case NM_SETTING_DIFF_RESULT_IN_B:
-					nm_log (level, domain, NULL, NULL, "%s%"_NM_LOG_ALIGN"s < %s", prefix, str1->str, str_diff ?: "NULL");
-					break;
-				case NM_SETTING_DIFF_RESULT_IN_A:
-					nm_log (level, domain, NULL, NULL, "%s%"_NM_LOG_ALIGN"s = %s", prefix, str1->str, str_conn ?: "NULL");
-					break;
-				default:
-					nm_log (level, domain, NULL, NULL, "%s%"_NM_LOG_ALIGN"s = %s < %s", prefix, str1->str, str_conn ?: "NULL", str_diff ?: "NULL");
-					break;
+            if (print_setting_header) {
+                if (diff_base) {
+                    if (setting_data->setting && setting_data->diff_base_setting)
+                        g_string_printf(str1,
+                                        "%p < %p",
+                                        setting_data->setting,
+                                        setting_data->diff_base_setting);
+                    else if (setting_data->diff_base_setting)
+                        g_string_printf(str1, "*missing* < %p", setting_data->diff_base_setting);
+                    else
+                        g_string_printf(str1, "%p < *missing*", setting_data->setting);
+                    nm_log(level,
+                           domain,
+                           NULL,
+                           NULL,
+                           "%s%"_NM_LOG_ALIGN
+                           "s [ %s ]",
+                           prefix,
+                           setting_data->name,
+                           str1->str);
+                } else
+                    nm_log(level,
+                           domain,
+                           NULL,
+                           NULL,
+                           "%s%"_NM_LOG_ALIGN
+                           "s [ %p ]",
+                           prefix,
+                           setting_data->name,
+                           setting_data->setting);
+                print_setting_header = FALSE;
+            }
+            g_string_printf(str1, "%s.%s", setting_data->name, item->item_name);
+            switch (item->diff_result
+                    & (NM_SETTING_DIFF_RESULT_IN_A | NM_SETTING_DIFF_RESULT_IN_B)) {
+            case NM_SETTING_DIFF_RESULT_IN_B:
+                nm_log(level,
+                       domain,
+                       NULL,
+                       NULL,
+                       "%s%"_NM_LOG_ALIGN
+                       "s < %s",
+                       prefix,
+                       str1->str,
+                       str_diff ?: "NULL");
+                break;
+            case NM_SETTING_DIFF_RESULT_IN_A:
+                nm_log(level,
+                       domain,
+                       NULL,
+                       NULL,
+                       "%s%"_NM_LOG_ALIGN
+                       "s = %s",
+                       prefix,
+                       str1->str,
+                       str_conn ?: "NULL");
+                break;
+            default:
+                nm_log(level,
+                       domain,
+                       NULL,
+                       NULL,
+                       "%s%"_NM_LOG_ALIGN
+                       "s = %s < %s",
+                       prefix,
+                       str1->str,
+                       str_conn ?: "NULL",
+                       str_diff ?: "NULL");
+                break;
 #undef _NM_LOG_ALIGN
-			}
-			g_free (str_conn);
-			g_free (str_diff);
-		}
-	}
-
-	g_array_free (sorted_names, TRUE);
-	g_string_free (str1, TRUE);
+            }
+            g_free(str_conn);
+            g_free(str_diff);
+        }
+    }
+
+    g_array_free(sorted_names, TRUE);
+    g_string_free(str1, TRUE);
 out:
-	g_hash_table_destroy (connection_diff);
-	g_array_free (sorted_hashes, TRUE);
+    g_hash_table_destroy(connection_diff);
+    g_array_free(sorted_hashes, TRUE);
 }
 
 #define IPV6_PROPERTY_DIR "/proc/sys/net/ipv6/conf/"
 #define IPV4_PROPERTY_DIR "/proc/sys/net/ipv4/conf/"
-G_STATIC_ASSERT (sizeof (IPV4_PROPERTY_DIR) == sizeof (IPV6_PROPERTY_DIR));
-G_STATIC_ASSERT (NM_STRLEN (IPV6_PROPERTY_DIR) + IFNAMSIZ + 60 == NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE);
+G_STATIC_ASSERT(sizeof(IPV4_PROPERTY_DIR) == sizeof(IPV6_PROPERTY_DIR));
+G_STATIC_ASSERT(NM_STRLEN(IPV6_PROPERTY_DIR) + IFNAMSIZ + 60
+                == NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE);
 
 /**
  * nm_utils_sysctl_ip_conf_path:
@@ -2268,517 +2562,538 @@ G_STATIC_ASSERT (NM_STRLEN (IPV6_PROPERTY_DIR) + IFNAMSIZ + 60 == NM_UTILS_SYSCT
  * this returns the input argument @buf.
  */
 const char *
-nm_utils_sysctl_ip_conf_path (int addr_family, char *buf, const char *ifname, const char *property)
+nm_utils_sysctl_ip_conf_path(int addr_family, char *buf, const char *ifname, const char *property)
 {
-	int len;
-
-	nm_assert (buf);
-	nm_assert_addr_family (addr_family);
-
-	g_assert (nm_utils_ifname_valid_kernel (ifname, NULL));
-	property = NM_ASSERT_VALID_PATH_COMPONENT (property);
-
-	len = g_snprintf (buf,
-	                  NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE,
-	                  "%s%s/%s",
-	                  addr_family == AF_INET6 ? IPV6_PROPERTY_DIR : IPV4_PROPERTY_DIR,
-	                  ifname,
-	                  property);
-	g_assert (len < NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE - 1);
-	return buf;
+    int len;
+
+    nm_assert(buf);
+    nm_assert_addr_family(addr_family);
+
+    g_assert(nm_utils_ifname_valid_kernel(ifname, NULL));
+    property = NM_ASSERT_VALID_PATH_COMPONENT(property);
+
+    len = g_snprintf(buf,
+                     NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE,
+                     "%s%s/%s",
+                     addr_family == AF_INET6 ? IPV6_PROPERTY_DIR : IPV4_PROPERTY_DIR,
+                     ifname,
+                     property);
+    g_assert(len < NM_UTILS_SYSCTL_IP_CONF_PATH_BUFSIZE - 1);
+    return buf;
 }
 
 gboolean
-nm_utils_sysctl_ip_conf_is_path (int addr_family, const char *path, const char *ifname, const char *property)
+nm_utils_sysctl_ip_conf_is_path(int         addr_family,
+                                const char *path,
+                                const char *ifname,
+                                const char *property)
 {
-	g_return_val_if_fail (path, FALSE);
-	NM_ASSERT_VALID_PATH_COMPONENT (property);
-	g_assert (!ifname || nm_utils_ifname_valid_kernel (ifname, NULL));
-
-	if (addr_family == AF_INET) {
-		if (!g_str_has_prefix (path, IPV4_PROPERTY_DIR))
-			return FALSE;
-		path += NM_STRLEN (IPV4_PROPERTY_DIR);
-	} else if (addr_family == AF_INET6) {
-		if (!g_str_has_prefix (path, IPV6_PROPERTY_DIR))
-			return FALSE;
-		path += NM_STRLEN (IPV6_PROPERTY_DIR);
-	} else
-		g_return_val_if_reached (FALSE);
-
-	if (ifname) {
-		if (!g_str_has_prefix (path, ifname))
-			return FALSE;
-		path += strlen (ifname);
-		if (path[0] != '/')
-			return FALSE;
-		path++;
-	} else {
-		const char *slash;
-		char buf[IFNAMSIZ];
-		gsize l;
-
-		slash = strchr (path, '/');
-		if (!slash)
-			return FALSE;
-		l = slash - path;
-		if (l >= IFNAMSIZ)
-			return FALSE;
-		memcpy (buf, path, l);
-		buf[l] = '\0';
-		if (!nm_utils_ifname_valid_kernel (buf, NULL))
-			return FALSE;
-		path = slash + 1;
-	}
-
-	if (!nm_streq (path, property))
-		return FALSE;
-
-	return TRUE;
+    g_return_val_if_fail(path, FALSE);
+    NM_ASSERT_VALID_PATH_COMPONENT(property);
+    g_assert(!ifname || nm_utils_ifname_valid_kernel(ifname, NULL));
+
+    if (addr_family == AF_INET) {
+        if (!g_str_has_prefix(path, IPV4_PROPERTY_DIR))
+            return FALSE;
+        path += NM_STRLEN(IPV4_PROPERTY_DIR);
+    } else if (addr_family == AF_INET6) {
+        if (!g_str_has_prefix(path, IPV6_PROPERTY_DIR))
+            return FALSE;
+        path += NM_STRLEN(IPV6_PROPERTY_DIR);
+    } else
+        g_return_val_if_reached(FALSE);
+
+    if (ifname) {
+        if (!g_str_has_prefix(path, ifname))
+            return FALSE;
+        path += strlen(ifname);
+        if (path[0] != '/')
+            return FALSE;
+        path++;
+    } else {
+        const char *slash;
+        char        buf[IFNAMSIZ];
+        gsize       l;
+
+        slash = strchr(path, '/');
+        if (!slash)
+            return FALSE;
+        l = slash - path;
+        if (l >= IFNAMSIZ)
+            return FALSE;
+        memcpy(buf, path, l);
+        buf[l] = '\0';
+        if (!nm_utils_ifname_valid_kernel(buf, NULL))
+            return FALSE;
+        path = slash + 1;
+    }
+
+    if (!nm_streq(path, property))
+        return FALSE;
+
+    return TRUE;
 }
 
 gboolean
-nm_utils_is_valid_path_component (const char *name)
+nm_utils_is_valid_path_component(const char *name)
 {
-	const char *n;
-
-	if (name == NULL || name[0] == '\0')
-		return FALSE;
-
-	if (name[0] == '.') {
-		if (name[1] == '\0')
-			return FALSE;
-		if (name[1] == '.' && name[2] == '\0')
-			return FALSE;
-	}
-	n = name;
-	do {
-		if (*n == '/')
-			return FALSE;
-	} while (*(++n) != '\0');
-
-	return TRUE;
+    const char *n;
+
+    if (name == NULL || name[0] == '\0')
+        return FALSE;
+
+    if (name[0] == '.') {
+        if (name[1] == '\0')
+            return FALSE;
+        if (name[1] == '.' && name[2] == '\0')
+            return FALSE;
+    }
+    n = name;
+    do {
+        if (*n == '/')
+            return FALSE;
+    } while (*(++n) != '\0');
+
+    return TRUE;
 }
 
 const char *
-NM_ASSERT_VALID_PATH_COMPONENT (const char *name)
-{
-	if (G_LIKELY (nm_utils_is_valid_path_component (name)))
-		return name;
-
-	nm_log_err (LOGD_CORE, "Failed asserting path component: %s%s%s",
-	            NM_PRINT_FMT_QUOTED (name, "\"", name, "\"", "(null)"));
-	g_error ("FATAL: Failed asserting path component: %s%s%s",
-	         NM_PRINT_FMT_QUOTED (name, "\"", name, "\"", "(null)"));
-	g_assert_not_reached ();
-}
-
-gboolean
-nm_utils_is_specific_hostname (const char *name)
+NM_ASSERT_VALID_PATH_COMPONENT(const char *name)
 {
-	if (!name)
-		return FALSE;
-	if (   strcmp (name, "(none)")
-	    && strcmp (name, "localhost")
-	    && strcmp (name, "localhost6")
-	    && strcmp (name, "localhost.localdomain")
-	    && strcmp (name, "localhost6.localdomain6"))
-		return TRUE;
-	return FALSE;
+    if (G_LIKELY(nm_utils_is_valid_path_component(name)))
+        return name;
+
+    nm_log_err(LOGD_CORE,
+               "Failed asserting path component: %s%s%s",
+               NM_PRINT_FMT_QUOTED(name, "\"", name, "\"", "(null)"));
+    g_error("FATAL: Failed asserting path component: %s%s%s",
+            NM_PRINT_FMT_QUOTED(name, "\"", name, "\"", "(null)"));
+    g_assert_not_reached();
 }
 
 /*****************************************************************************/
 
 typedef struct {
-	NMUuid bin;
-	char _nul_sentinel; /* just for safety, if somebody accidentally uses the binary in a string context. */
-
-	/* depending on whether the string is packed or not (with/without hyphens),
-	 * it's 32 or 36 characters long (plus the trailing NUL).
-	 *
-	 * The difference is that boot-id is a valid RFC 4211 UUID and represented
-	 * as a 36 ascii string (with hyphens). The machine-id technically is not
-	 * a UUID, but just a 32 byte sequence of hexchars. */
-	char str[37];
-	bool is_fake;
+    NMUuid bin;
+    char
+        _nul_sentinel; /* just for safety, if somebody accidentally uses the binary in a string context. */
+
+    /* depending on whether the string is packed or not (with/without hyphens),
+     * it's 32 or 36 characters long (plus the trailing NUL).
+     *
+     * The difference is that boot-id is a valid RFC 4211 UUID and represented
+     * as a 36 ascii string (with hyphens). The machine-id technically is not
+     * a UUID, but just a 32 byte sequence of hexchars. */
+    char str[37];
+    bool is_fake;
 } UuidData;
 
 static UuidData *
-_uuid_data_init (UuidData *uuid_data,
-                 gboolean packed,
-                 gboolean is_fake,
-                 const NMUuid *uuid)
+_uuid_data_init(UuidData *uuid_data, gboolean packed, gboolean is_fake, const NMUuid *uuid)
 {
-	nm_assert (uuid_data);
-	nm_assert (uuid);
-
-	uuid_data->bin = *uuid;
-	uuid_data->_nul_sentinel = '\0';
-	uuid_data->is_fake = is_fake;
-	if (packed) {
-		G_STATIC_ASSERT_EXPR (sizeof (uuid_data->str) >= (sizeof (*uuid) * 2 + 1));
-		nm_utils_bin2hexstr_full (uuid,
-		                          sizeof (*uuid),
-		                          '\0',
-		                          FALSE,
-		                          uuid_data->str);
-	} else {
-		G_STATIC_ASSERT_EXPR (sizeof (uuid_data->str) >= 37);
-		_nm_utils_uuid_unparse (uuid, uuid_data->str);
-	}
-	return uuid_data;
+    nm_assert(uuid_data);
+    nm_assert(uuid);
+
+    uuid_data->bin           = *uuid;
+    uuid_data->_nul_sentinel = '\0';
+    uuid_data->is_fake       = is_fake;
+    if (packed) {
+        G_STATIC_ASSERT_EXPR(sizeof(uuid_data->str) >= (sizeof(*uuid) * 2 + 1));
+        nm_utils_bin2hexstr_full(uuid, sizeof(*uuid), '\0', FALSE, uuid_data->str);
+    } else {
+        G_STATIC_ASSERT_EXPR(sizeof(uuid_data->str) >= 37);
+        _nm_utils_uuid_unparse(uuid, uuid_data->str);
+    }
+    return uuid_data;
 }
 
 /*****************************************************************************/
 
 static const UuidData *
-_machine_id_get (gboolean allow_fake)
+_machine_id_get(gboolean allow_fake)
 {
-	static const UuidData *volatile p_uuid_data;
-	const UuidData *d;
+    static const UuidData *volatile p_uuid_data;
+    const UuidData *d;
 
 again:
-	d = g_atomic_pointer_get (&p_uuid_data);
-	if (G_UNLIKELY (!d)) {
-		static gsize lock;
-		static UuidData uuid_data;
-		gs_free char *content = NULL;
-		gboolean is_fake = TRUE;
-		const char *fake_type = NULL;
-		NMUuid uuid;
-
-		/* Get the machine ID from /etc/machine-id; it's always in /etc no matter
-		 * where our configured SYSCONFDIR is.  Alternatively, it might be in
-		 * LOCALSTATEDIR /lib/dbus/machine-id.
-		 */
-		if (   nm_utils_file_get_contents (-1, "/etc/machine-id",                   100*1024, 0, &content, NULL, NULL, NULL)
-		    || nm_utils_file_get_contents (-1, LOCALSTATEDIR"/lib/dbus/machine-id", 100*1024, 0, &content, NULL, NULL, NULL)) {
-			g_strstrip (content);
-			if (nm_utils_hexstr2bin_full (content,
-			                              FALSE,
-			                              FALSE,
-			                              NULL,
-			                              16,
-			                              (guint8 *) &uuid,
-			                              sizeof (uuid),
-			                              NULL)) {
-				if (!nm_utils_uuid_is_null (&uuid)) {
-					/* an all-zero machine-id is not valid. */
-					is_fake = FALSE;
-				}
-			}
-		}
-
-		if (is_fake) {
-			const guint8 *seed_bin;
-			const char *hash_seed;
-			gsize seed_len;
-
-			if (!allow_fake) {
-				/* we don't allow generating (and memoizing) a fake key.
-				 * Signal that no valid machine-id exists. */
-				return NULL;
-			}
-
-			if (nm_utils_host_id_get (&seed_bin, &seed_len)) {
-				/* we have no valid machine-id. Generate a fake one by hashing
-				 * the secret-key. This key is commonly persisted, so it should be
-				 * stable across reboots (despite having a broken system without
-				 * proper machine-id). */
-				fake_type = "secret-key";
-				hash_seed = "ab085f06-b629-46d1-a553-84eeba5683b6";
-			} else {
-				/* the secret-key is not valid/persistent either. That happens when we fail
-				 * to read/write the secret-key to disk. Fallback to boot-id. The boot-id
-				 * itself may be fake and randomly generated ad-hoc, but that is as best
-				 * as it gets.  */
-				seed_bin = (const guint8 *) nm_utils_boot_id_bin ();
-				seed_len = sizeof (NMUuid);
-				fake_type = "boot-id";
-				hash_seed = "7ff0c8f5-5399-4901-ab63-61bf594abe8b";
-			}
-
-			/* the fake machine-id is based on secret-key/boot-id, but we hash it
-			 * again, so that they are not literally the same. */
-			nm_utils_uuid_generate_from_string_bin (&uuid,
-			                                        (const char *) seed_bin,
-			                                        seed_len,
-			                                        NM_UTILS_UUID_TYPE_VERSION5,
-			                                        (gpointer) hash_seed);
-		}
-
-		if (!g_once_init_enter (&lock))
-			goto again;
-
-		d = _uuid_data_init (&uuid_data, TRUE, is_fake, &uuid);
-		g_atomic_pointer_set (&p_uuid_data, d);
-		g_once_init_leave (&lock, 1);
-
-		if (is_fake) {
-			nm_log_err (LOGD_CORE,
-			            "/etc/machine-id: no valid machine-id. Use fake one based on %s: %s",
-			            fake_type,
-			            d->str);
-		} else
-			nm_log_dbg (LOGD_CORE, "/etc/machine-id: %s", d->str);
-	}
-
-	return d;
+    d = g_atomic_pointer_get(&p_uuid_data);
+    if (G_UNLIKELY(!d)) {
+        static gsize    lock;
+        static UuidData uuid_data;
+        gs_free char *  content   = NULL;
+        gboolean        is_fake   = TRUE;
+        const char *    fake_type = NULL;
+        NMUuid          uuid;
+
+        /* Get the machine ID from /etc/machine-id; it's always in /etc no matter
+         * where our configured SYSCONFDIR is.  Alternatively, it might be in
+         * LOCALSTATEDIR /lib/dbus/machine-id.
+         */
+        if (nm_utils_file_get_contents(-1,
+                                       "/etc/machine-id",
+                                       100 * 1024,
+                                       0,
+                                       &content,
+                                       NULL,
+                                       NULL,
+                                       NULL)
+            || nm_utils_file_get_contents(-1,
+                                          LOCALSTATEDIR "/lib/dbus/machine-id",
+                                          100 * 1024,
+                                          0,
+                                          &content,
+                                          NULL,
+                                          NULL,
+                                          NULL)) {
+            g_strstrip(content);
+            if (nm_utils_hexstr2bin_full(content,
+                                         FALSE,
+                                         FALSE,
+                                         FALSE,
+                                         NULL,
+                                         16,
+                                         (guint8 *) &uuid,
+                                         sizeof(uuid),
+                                         NULL)) {
+                if (!nm_utils_uuid_is_null(&uuid)) {
+                    /* an all-zero machine-id is not valid. */
+                    is_fake = FALSE;
+                }
+            }
+        }
+
+        if (is_fake) {
+            const guint8 *seed_bin;
+            const char *  hash_seed;
+            gsize         seed_len;
+
+            if (!allow_fake) {
+                /* we don't allow generating (and memorizing) a fake key.
+                 * Signal that no valid machine-id exists. */
+                return NULL;
+            }
+
+            if (nm_utils_host_id_get(&seed_bin, &seed_len)) {
+                /* We have no valid machine-id but we have a valid secrey_key.
+                 * Generate a fake machine ID by hashing the secret-key. The secret_key
+                 * is commonly persisted, so it should be stable across reboots (despite
+                 * having a broken system without proper machine-id).
+                 *
+                 * Note that we access the host-id here, which is based on secret_key.
+                 * Also not that the secret_key may be generated based on the machine-id,
+                 * so we have to be careful that they don't depend on each other (and
+                 * no infinite recursion happens. This is done correctly, because the secret-key
+                 * will call _machine_id_get(FALSE), so it won't allow accessing a fake
+                 * machine-id, thus avoiding the problem. */
+                fake_type = "secret-key";
+                hash_seed = "ab085f06-b629-46d1-a553-84eeba5683b6";
+            } else {
+                /* the secret-key is not valid/persistent either. That happens when we fail
+                 * to read/write the secret-key to disk. Fallback to boot-id. The boot-id
+                 * itself may be fake and randomly generated ad-hoc, but that is as best
+                 * as it gets.  */
+                seed_bin  = (const guint8 *) nm_utils_boot_id_bin();
+                seed_len  = sizeof(NMUuid);
+                fake_type = "boot-id";
+                hash_seed = "7ff0c8f5-5399-4901-ab63-61bf594abe8b";
+            }
+
+            /* the fake machine-id is based on secret-key/boot-id, but we hash it
+             * again, so that they are not literally the same. */
+            nm_utils_uuid_generate_from_string_bin(&uuid,
+                                                   (const char *) seed_bin,
+                                                   seed_len,
+                                                   NM_UTILS_UUID_TYPE_VERSION5,
+                                                   (gpointer) hash_seed);
+        }
+
+        if (!g_once_init_enter(&lock))
+            goto again;
+
+        d = _uuid_data_init(&uuid_data, TRUE, is_fake, &uuid);
+        g_atomic_pointer_set(&p_uuid_data, d);
+        g_once_init_leave(&lock, 1);
+
+        if (is_fake) {
+            nm_log_err(LOGD_CORE,
+                       "/etc/machine-id: no valid machine-id. Use fake one based on %s: %s",
+                       fake_type,
+                       d->str);
+        } else
+            nm_log_dbg(LOGD_CORE, "/etc/machine-id: %s", d->str);
+    }
+
+    return d;
 }
 
 const char *
-nm_utils_machine_id_str (void)
+nm_utils_machine_id_str(void)
 {
-	return _machine_id_get (TRUE)->str;
+    return _machine_id_get(TRUE)->str;
 }
 
 const NMUuid *
-nm_utils_machine_id_bin (void)
+nm_utils_machine_id_bin(void)
 {
-	return &_machine_id_get (TRUE)->bin;
+    return &_machine_id_get(TRUE)->bin;
 }
 
 gboolean
-nm_utils_machine_id_is_fake (void)
+nm_utils_machine_id_is_fake(void)
 {
-	return _machine_id_get (TRUE)->is_fake;
+    return _machine_id_get(TRUE)->is_fake;
 }
 
 /*****************************************************************************/
 
 /* prefix for version2 secret key. The secret key is hashed with /etc/machine-id. */
 #define SECRET_KEY_V2_PREFIX "nm-v2:"
-#define SECRET_KEY_FILE      NMSTATEDIR"/secret_key"
+#define SECRET_KEY_FILE      NMSTATEDIR "/secret_key"
 
 static gboolean
-_host_id_read_timestamp (gboolean use_secret_key_file,
-                         const guint8 *host_id,
-                         gsize host_id_len,
-                         gint64 *out_timestamp_ns)
+_host_id_read_timestamp(gboolean      use_secret_key_file,
+                        const guint8 *host_id,
+                        gsize         host_id_len,
+                        gint64 *      out_timestamp_ns)
 {
-	struct stat st;
-	gint64 now;
-	guint64 v;
-
-	if (   use_secret_key_file
-	    && stat (SECRET_KEY_FILE, &st) == 0) {
-		/* don't check for overflow or timestamps in the future. We get whatever
-		 * (bogus) date is on the file. */
-		*out_timestamp_ns = nm_utils_timespec_to_nsec (&st.st_mtim);
-		return TRUE;
-	}
-
-	/* generate a fake timestamp based on the host-id.
-	 *
-	 * This really should never happen under normal circumstances. We already
-	 * are in a code path, where the system has a problem (unable to get good randomness
-	 * and/or can't access the secret_key). In such a scenario, a fake timestamp is the
-	 * least of our problems.
-	 *
-	 * At least, generate something sensible so we don't have to worry about the
-	 * timestamp. It is wrong to worry about using a fake timestamp (which is tied to
-	 * the secret_key) if we are unable to access the secret_key file in the first place.
-	 *
-	 * Pick a random timestamp from the past two years. Yes, this timestamp
-	 * is not stable across restarts, but apparently neither is the host-id
-	 * nor the secret_key itself. */
-
-#define EPOCH_TWO_YEARS  (G_GINT64_CONSTANT (2 * 365 * 24 * 3600) * NM_UTILS_NSEC_PER_SEC)
-
-	v = nm_hash_siphash42 (1156657133u, host_id, host_id_len);
-
-	now = time (NULL);
-	*out_timestamp_ns = NM_MAX ((gint64) 1,
-	                            (now * NM_UTILS_NSEC_PER_SEC) - ((gint64) (v % ((guint64) (EPOCH_TWO_YEARS)))));
-	return FALSE;
+    struct stat st;
+    gint64      now;
+    guint64     v;
+
+    if (use_secret_key_file && stat(SECRET_KEY_FILE, &st) == 0) {
+        /* don't check for overflow or timestamps in the future. We get whatever
+         * (bogus) date is on the file. */
+        *out_timestamp_ns = nm_utils_timespec_to_nsec(&st.st_mtim);
+        return TRUE;
+    }
+
+    /* generate a fake timestamp based on the host-id.
+     *
+     * This really should never happen under normal circumstances. We already
+     * are in a code path, where the system has a problem (unable to get good randomness
+     * and/or can't access the secret_key). In such a scenario, a fake timestamp is the
+     * least of our problems.
+     *
+     * At least, generate something sensible so we don't have to worry about the
+     * timestamp. It is wrong to worry about using a fake timestamp (which is tied to
+     * the secret_key) if we are unable to access the secret_key file in the first place.
+     *
+     * Pick a random timestamp from the past two years. Yes, this timestamp
+     * is not stable across restarts, but apparently neither is the host-id
+     * nor the secret_key itself. */
+
+#define EPOCH_TWO_YEARS (G_GINT64_CONSTANT(2 * 365 * 24 * 3600) * NM_UTILS_NSEC_PER_SEC)
+
+    v = nm_hash_siphash42(1156657133u, host_id, host_id_len);
+
+    now = time(NULL);
+    *out_timestamp_ns =
+        NM_MAX((gint64) 1,
+               (now * NM_UTILS_NSEC_PER_SEC) - ((gint64)(v % ((guint64)(EPOCH_TWO_YEARS)))));
+    return FALSE;
 }
 
 static const guint8 *
-_host_id_hash_v2 (const guint8 *seed_arr,
-                  gsize seed_len,
-                  guint8 *out_digest /* 32 bytes (NM_UTILS_CHECKSUM_LENGTH_SHA256) */)
+_host_id_hash_v2(const guint8 *seed_arr,
+                 gsize         seed_len,
+                 guint8 *      out_digest /* 32 bytes (NM_UTILS_CHECKSUM_LENGTH_SHA256) */)
 {
-	nm_auto_free_checksum GChecksum *sum = g_checksum_new (G_CHECKSUM_SHA256);
-	const UuidData *machine_id_data;
-	char slen[100];
+    nm_auto_free_checksum GChecksum *sum = g_checksum_new(G_CHECKSUM_SHA256);
+    const UuidData *                 machine_id_data;
+    char                             slen[100];
 
-	/*
-	    (stat -c '%s' /var/lib/NetworkManager/secret_key;
-	     echo -n ' ';
-	     cat /var/lib/NetworkManager/secret_key;
-	     cat /etc/machine-id | tr -d '\n' | sed -n 's/[a-f0-9-]/\0/pg') | sha256sum
-	*/
+    /*
+        (stat -c '%s' /var/lib/NetworkManager/secret_key;
+         echo -n ' ';
+         cat /var/lib/NetworkManager/secret_key;
+         cat /etc/machine-id | tr -d '\n' | sed -n 's/[a-f0-9-]/\0/pg') | sha256sum
+    */
 
-	nm_sprintf_buf (slen, "%"G_GSIZE_FORMAT" ", seed_len);
-	g_checksum_update (sum, (const guchar *) slen, strlen (slen));
+    nm_sprintf_buf(slen, "%" G_GSIZE_FORMAT " ", seed_len);
+    g_checksum_update(sum, (const guchar *) slen, strlen(slen));
 
-	g_checksum_update (sum, (const guchar *) seed_arr, seed_len);
+    g_checksum_update(sum, (const guchar *) seed_arr, seed_len);
 
-	machine_id_data = _machine_id_get (FALSE);
-	if (   machine_id_data
-	    && !machine_id_data->is_fake)
-		g_checksum_update (sum, (const guchar *) machine_id_data->str, strlen (machine_id_data->str));
+    machine_id_data = _machine_id_get(FALSE);
+    if (machine_id_data && !machine_id_data->is_fake)
+        g_checksum_update(sum, (const guchar *) machine_id_data->str, strlen(machine_id_data->str));
 
-	nm_utils_checksum_get_digest_len (sum, out_digest, NM_UTILS_CHECKSUM_LENGTH_SHA256);
-	return out_digest;
+    nm_utils_checksum_get_digest_len(sum, out_digest, NM_UTILS_CHECKSUM_LENGTH_SHA256);
+    return out_digest;
 }
 
 static gboolean
-_host_id_read (guint8 **out_host_id,
-               gsize *out_host_id_len)
+_host_id_read(guint8 **out_host_id, gsize *out_host_id_len)
 {
 #define SECRET_KEY_LEN 32u
-	guint8 sha256_digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
-	nm_auto_clear_secret_ptr NMSecretPtr file_content = { 0 };
-	const guint8 *secret_arr;
-	gsize secret_len;
-	GError *error = NULL;
-	gboolean success;
-
-	if (!nm_utils_file_get_contents (-1,
-	                                 SECRET_KEY_FILE,
-	                                 10*1024,
-	                                 NM_UTILS_FILE_GET_CONTENTS_FLAG_SECRET,
-	                                 &file_content.str,
-	                                 &file_content.len,
-	                                 NULL,
-	                                 &error)) {
-		if (!nm_utils_error_is_notfound (error)) {
-			nm_log_warn (LOGD_CORE, "secret-key: failure reading secret key in \"%s\": %s (generate new key)",
-			             SECRET_KEY_FILE, error->message);
-		}
-		g_clear_error (&error);
-	} else if (   file_content.len >= NM_STRLEN (SECRET_KEY_V2_PREFIX) + SECRET_KEY_LEN
-	           && memcmp (file_content.bin, SECRET_KEY_V2_PREFIX, NM_STRLEN (SECRET_KEY_V2_PREFIX)) == 0) {
-		/* for this type of secret key, we require a prefix followed at least SECRET_KEY_LEN (32) bytes. We
-		 * (also) do that, because older versions of NetworkManager wrote exactly 32 bytes without
-		 * prefix, so we won't wrongly interpret such legacy keys as v2 (if they accidentally have
-		 * a SECRET_KEY_V2_PREFIX prefix, they'll still have the wrong size).
-		 *
-		 * Note that below we generate the random seed in base64 encoding. But that is only done
-		 * to write an ASCII file. There is no base64 decoding and the ASCII is hashed as-is.
-		 * We would accept any binary data just as well (provided a suitable prefix and at least
-		 * 32 bytes).
-		 *
-		 * Note that when hashing the v2 content, we also hash the prefix. There is no strong reason,
-		 * except that it seems simpler not to distinguish between the v2 prefix and the content.
-		 * It's all just part of the seed. */
-
-		secret_arr = _host_id_hash_v2 (file_content.bin, file_content.len, sha256_digest);
-		secret_len = NM_UTILS_CHECKSUM_LENGTH_SHA256;
-		success = TRUE;
-		goto out;
-	} else if (file_content.len >= 16) {
-		secret_arr = file_content.bin;
-		secret_len = file_content.len;
-		success = TRUE;
-		goto out;
-	} else {
-		/* the secret key is borked. Log a warning, but proceed below to generate
-		 * a new one. */
-		nm_log_warn (LOGD_CORE, "secret-key: too short secret key in \"%s\" (generate new key)", SECRET_KEY_FILE);
-	}
-
-	/* generate and persist new key */
-	{
+    guint8                               sha256_digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
+    nm_auto_clear_secret_ptr NMSecretPtr file_content = {0};
+    const guint8 *                       secret_arr;
+    gsize                                secret_len;
+    GError *                             error = NULL;
+    gboolean                             success;
+
+    if (!nm_utils_file_get_contents(-1,
+                                    SECRET_KEY_FILE,
+                                    10 * 1024,
+                                    NM_UTILS_FILE_GET_CONTENTS_FLAG_SECRET,
+                                    &file_content.str,
+                                    &file_content.len,
+                                    NULL,
+                                    &error)) {
+        if (!nm_utils_error_is_notfound(error)) {
+            nm_log_warn(LOGD_CORE,
+                        "secret-key: failure reading secret key in \"%s\": %s (generate new key)",
+                        SECRET_KEY_FILE,
+                        error->message);
+        }
+        g_clear_error(&error);
+    } else if (file_content.len >= NM_STRLEN(SECRET_KEY_V2_PREFIX) + SECRET_KEY_LEN
+               && memcmp(file_content.bin, SECRET_KEY_V2_PREFIX, NM_STRLEN(SECRET_KEY_V2_PREFIX))
+                      == 0) {
+        /* for this type of secret key, we require a prefix followed at least SECRET_KEY_LEN (32) bytes. We
+         * (also) do that, because older versions of NetworkManager wrote exactly 32 bytes without
+         * prefix, so we won't wrongly interpret such legacy keys as v2 (if they accidentally have
+         * a SECRET_KEY_V2_PREFIX prefix, they'll still have the wrong size).
+         *
+         * Note that below we generate the random seed in base64 encoding. But that is only done
+         * to write an ASCII file. There is no base64 decoding and the ASCII is hashed as-is.
+         * We would accept any binary data just as well (provided a suitable prefix and at least
+         * 32 bytes).
+         *
+         * Note that when hashing the v2 content, we also hash the prefix. There is no strong reason,
+         * except that it seems simpler not to distinguish between the v2 prefix and the content.
+         * It's all just part of the seed. */
+
+        secret_arr = _host_id_hash_v2(file_content.bin, file_content.len, sha256_digest);
+        secret_len = NM_UTILS_CHECKSUM_LENGTH_SHA256;
+        success    = TRUE;
+        nm_log_dbg(LOGD_CORE,
+                   "secret-key: v2 secret key loaded from \"%s\" (%zu bytes)",
+                   SECRET_KEY_FILE,
+                   file_content.len);
+        goto out;
+    } else if (file_content.len >= 16) {
+        secret_arr = file_content.bin;
+        secret_len = file_content.len;
+        success    = TRUE;
+        nm_log_dbg(LOGD_CORE,
+                   "secret-key: v1 secret key loaded from \"%s\" (%zu bytes)",
+                   SECRET_KEY_FILE,
+                   file_content.len);
+        goto out;
+    } else {
+        /* the secret key is borked. Log a warning, but proceed below to generate
+         * a new one. */
+        nm_log_warn(LOGD_CORE,
+                    "secret-key: too short secret key in \"%s\" (generate new key)",
+                    SECRET_KEY_FILE);
+    }
+
+    /* generate and persist new key */
+    {
 #define SECRET_KEY_LEN_BASE64 ((((SECRET_KEY_LEN / 3) + 1) * 4) + 4)
-		guint8 rnd_buf[SECRET_KEY_LEN];
-		guint8 new_content[NM_STRLEN (SECRET_KEY_V2_PREFIX) + SECRET_KEY_LEN_BASE64];
-		int base64_state = 0;
-		int base64_save = 0;
-		gsize len;
-
-		success = nm_utils_random_bytes (rnd_buf, sizeof (rnd_buf));
-
-		/* Our key is really binary data. But since we anyway generate a random seed
-		 * (with 32 random bytes), don't write it in binary, but instead create
-		 * an pure ASCII (base64) representation. Note that the ASCII will still be taken
-		 * as-is (no base64 decoding is done). The sole purpose is to write a ASCII file
-		 * instead of a binary. The content is gibberish either way. */
-		memcpy (new_content, SECRET_KEY_V2_PREFIX, NM_STRLEN (SECRET_KEY_V2_PREFIX));
-		len = NM_STRLEN (SECRET_KEY_V2_PREFIX);
-		len += g_base64_encode_step (rnd_buf,
-		                             sizeof (rnd_buf),
-		                             FALSE,
-		                             (char *) &new_content[len],
-		                             &base64_state,
-		                             &base64_save);
-		len += g_base64_encode_close (FALSE,
-		                              (char *) &new_content[len],
-		                              &base64_state,
-		                              &base64_save);
-		nm_assert (len <= sizeof (new_content));
-
-		secret_arr = _host_id_hash_v2 (new_content, len, sha256_digest);
-		secret_len = NM_UTILS_CHECKSUM_LENGTH_SHA256;
-
-		if (!success)
-			nm_log_warn (LOGD_CORE, "secret-key: failure to generate good random data for secret-key (use non-persistent key)");
-		else if (nm_utils_get_testing ()) {
-			/* for test code, we don't write the generated secret-key to disk. */
-		} else if (!nm_utils_file_set_contents (SECRET_KEY_FILE,
-		                                        (const char *) new_content,
-		                                        len,
-		                                        0600,
-		                                        NULL,
-		                                        &error)) {
-			nm_log_warn (LOGD_CORE, "secret-key: failure to persist secret key in \"%s\" (%s) (use non-persistent key)",
-			             SECRET_KEY_FILE, error->message);
-			g_clear_error (&error);
-			success = FALSE;
-		} else
-			nm_log_dbg (LOGD_CORE, "secret-key: persist new secret key to \"%s\"", SECRET_KEY_FILE);
-
-		nm_explicit_bzero (rnd_buf, sizeof (rnd_buf));
-		nm_explicit_bzero (new_content, sizeof (new_content));
-	}
+        guint8 rnd_buf[SECRET_KEY_LEN];
+        guint8 new_content[NM_STRLEN(SECRET_KEY_V2_PREFIX) + SECRET_KEY_LEN_BASE64];
+        int    base64_state = 0;
+        int    base64_save  = 0;
+        gsize  len;
+
+        success = nm_utils_random_bytes(rnd_buf, sizeof(rnd_buf));
+
+        /* Our key is really binary data. But since we anyway generate a random seed
+         * (with 32 random bytes), don't write it in binary, but instead create
+         * an pure ASCII (base64) representation. Note that the ASCII will still be taken
+         * as-is (no base64 decoding is done). The sole purpose is to write a ASCII file
+         * instead of a binary. The content is gibberish either way. */
+        memcpy(new_content, SECRET_KEY_V2_PREFIX, NM_STRLEN(SECRET_KEY_V2_PREFIX));
+        len = NM_STRLEN(SECRET_KEY_V2_PREFIX);
+        len += g_base64_encode_step(rnd_buf,
+                                    sizeof(rnd_buf),
+                                    FALSE,
+                                    (char *) &new_content[len],
+                                    &base64_state,
+                                    &base64_save);
+        len +=
+            g_base64_encode_close(FALSE, (char *) &new_content[len], &base64_state, &base64_save);
+        nm_assert(len <= sizeof(new_content));
+
+        secret_arr = _host_id_hash_v2(new_content, len, sha256_digest);
+        secret_len = NM_UTILS_CHECKSUM_LENGTH_SHA256;
+
+        if (!success)
+            nm_log_warn(LOGD_CORE,
+                        "secret-key: failure to generate good random data for secret-key (use "
+                        "non-persistent key)");
+        else if (nm_utils_get_testing()) {
+            /* for test code, we don't write the generated secret-key to disk. */
+        } else if (!nm_utils_file_set_contents(SECRET_KEY_FILE,
+                                               (const char *) new_content,
+                                               len,
+                                               0600,
+                                               NULL,
+                                               &error)) {
+            nm_log_warn(
+                LOGD_CORE,
+                "secret-key: failure to persist secret key in \"%s\" (%s) (use non-persistent key)",
+                SECRET_KEY_FILE,
+                error->message);
+            g_clear_error(&error);
+            success = FALSE;
+        } else
+            nm_log_dbg(LOGD_CORE,
+                       "secret-key: persist new v2 secret key to \"%s\" (%zu bytes)",
+                       SECRET_KEY_FILE,
+                       len);
+
+        nm_explicit_bzero(rnd_buf, sizeof(rnd_buf));
+        nm_explicit_bzero(new_content, sizeof(new_content));
+    }
 
 out:
-	*out_host_id_len = secret_len;
-	*out_host_id = nm_memdup (secret_arr, secret_len);
-	return success;
+    *out_host_id_len = secret_len;
+    *out_host_id     = nm_memdup(secret_arr, secret_len);
+    return success;
 }
 
 typedef struct {
-	guint8 *host_id;
-	gsize host_id_len;
-	gint64 timestamp_ns;
-	bool is_good:1;
-	bool timestamp_is_good:1;
+    guint8 *host_id;
+    gsize   host_id_len;
+    gint64  timestamp_ns;
+    bool    is_good : 1;
+    bool    timestamp_is_good : 1;
 } HostIdData;
 
 static const HostIdData *
-_host_id_get (void)
+_host_id_get(void)
 {
-	static const HostIdData *volatile host_id_static;
-	const HostIdData *host_id;
+    static const HostIdData *volatile host_id_static;
+    const HostIdData *host_id;
 
 again:
-	host_id = g_atomic_pointer_get (&host_id_static);
-	if (G_UNLIKELY (!host_id)) {
-		static HostIdData host_id_data;
-		static gsize init_value = 0;
-
-		if (!g_once_init_enter (&init_value))
-			goto again;
-
-		host_id_data.is_good = _host_id_read (&host_id_data.host_id,
-		                                      &host_id_data.host_id_len);
-
-		host_id_data.timestamp_is_good = _host_id_read_timestamp (host_id_data.is_good,
-		                                                          host_id_data.host_id,
-		                                                          host_id_data.host_id_len,
-		                                                          &host_id_data.timestamp_ns);
-		if (   !host_id_data.timestamp_is_good
-		    && host_id_data.is_good)
-			nm_log_warn (LOGD_CORE, "secret-key: failure reading host timestamp (use fake one)");
-
-		host_id = &host_id_data;
-		g_atomic_pointer_set (&host_id_static, host_id);
-		g_once_init_leave (&init_value, 1);
-	}
-
-	return host_id;
+    host_id = g_atomic_pointer_get(&host_id_static);
+    if (G_UNLIKELY(!host_id)) {
+        static HostIdData host_id_data;
+        static gsize      init_value = 0;
+
+        if (!g_once_init_enter(&init_value))
+            goto again;
+
+        host_id_data.is_good = _host_id_read(&host_id_data.host_id, &host_id_data.host_id_len);
+
+        host_id_data.timestamp_is_good = _host_id_read_timestamp(host_id_data.is_good,
+                                                                 host_id_data.host_id,
+                                                                 host_id_data.host_id_len,
+                                                                 &host_id_data.timestamp_ns);
+        if (!host_id_data.timestamp_is_good && host_id_data.is_good)
+            nm_log_warn(LOGD_CORE, "secret-key: failure reading host timestamp (use fake one)");
+
+        host_id = &host_id_data;
+        g_atomic_pointer_set(&host_id_static, host_id);
+        g_once_init_leave(&init_value, 1);
+    }
+
+    return host_id;
 }
 
 /**
@@ -2797,123 +3112,121 @@ again:
  *   to disk, and/or that it was generated with bad randomness.
  */
 gboolean
-nm_utils_host_id_get (const guint8 **out_host_id,
-                      gsize *out_host_id_len)
+nm_utils_host_id_get(const guint8 **out_host_id, gsize *out_host_id_len)
 {
-	const HostIdData *host_id;
+    const HostIdData *host_id;
 
-	host_id = _host_id_get ();
-	*out_host_id = host_id->host_id;
-	*out_host_id_len = host_id->host_id_len;
-	return host_id->is_good;
+    host_id          = _host_id_get();
+    *out_host_id     = host_id->host_id;
+    *out_host_id_len = host_id->host_id_len;
+    return host_id->is_good;
 }
 
 gint64
-nm_utils_host_id_get_timestamp_ns (void)
+nm_utils_host_id_get_timestamp_ns(void)
 {
-	return _host_id_get ()->timestamp_ns;
+    return _host_id_get()->timestamp_ns;
 }
 
 /*****************************************************************************/
 
 static const UuidData *
-_boot_id_get (void)
+_boot_id_get(void)
 {
-	static const UuidData *volatile p_boot_id;
-	const UuidData *d;
+    static const UuidData *volatile p_boot_id;
+    const UuidData *d;
 
 again:
-	d = g_atomic_pointer_get (&p_boot_id);
-	if (G_UNLIKELY (!d)) {
-		static gsize lock;
-		static UuidData boot_id;
-		gs_free char *contents = NULL;
-		NMUuid uuid;
-		gboolean is_fake = FALSE;
-
-		nm_utils_file_get_contents (-1,
-		                            "/proc/sys/kernel/random/boot_id",
-		                            0,
-		                            NM_UTILS_FILE_GET_CONTENTS_FLAG_NONE,
-		                            &contents,
-		                            NULL,
-		                            NULL,
-		                            NULL);
-		if (   !contents
-		    || !_nm_utils_uuid_parse (nm_strstrip (contents), &uuid)) {
-			/* generate a random UUID instead. */
-			is_fake = TRUE;
-			_nm_utils_uuid_generate_random (&uuid);
-		}
-
-		if (!g_once_init_enter (&lock))
-			goto again;
-
-		d = _uuid_data_init (&boot_id, FALSE, is_fake, &uuid);
-		g_atomic_pointer_set (&p_boot_id, d);
-		g_once_init_leave (&lock, 1);
-	}
-
-	return d;
+    d = g_atomic_pointer_get(&p_boot_id);
+    if (G_UNLIKELY(!d)) {
+        static gsize    lock;
+        static UuidData boot_id;
+        gs_free char *  contents = NULL;
+        NMUuid          uuid;
+        gboolean        is_fake = FALSE;
+
+        nm_utils_file_get_contents(-1,
+                                   "/proc/sys/kernel/random/boot_id",
+                                   0,
+                                   NM_UTILS_FILE_GET_CONTENTS_FLAG_NONE,
+                                   &contents,
+                                   NULL,
+                                   NULL,
+                                   NULL);
+        if (!contents || !_nm_utils_uuid_parse(nm_strstrip(contents), &uuid)) {
+            /* generate a random UUID instead. */
+            is_fake = TRUE;
+            _nm_utils_uuid_generate_random(&uuid);
+        }
+
+        if (!g_once_init_enter(&lock))
+            goto again;
+
+        d = _uuid_data_init(&boot_id, FALSE, is_fake, &uuid);
+        g_atomic_pointer_set(&p_boot_id, d);
+        g_once_init_leave(&lock, 1);
+    }
+
+    return d;
 }
 
 const char *
-nm_utils_boot_id_str (void)
+nm_utils_boot_id_str(void)
 {
-	return _boot_id_get ()->str;
+    return _boot_id_get()->str;
 }
 
 const NMUuid *
-nm_utils_boot_id_bin (void)
+nm_utils_boot_id_bin(void)
 {
-	return &_boot_id_get ()->bin;
+    return &_boot_id_get()->bin;
 }
 
 /*****************************************************************************/
 
 const char *
-nm_utils_proc_cmdline (void)
+nm_utils_proc_cmdline(void)
 {
-	static const char *volatile proc_cmdline_cached = NULL;
-	const char *proc_cmdline;
+    static const char *volatile proc_cmdline_cached = NULL;
+    const char *proc_cmdline;
 
 again:
-	proc_cmdline = g_atomic_pointer_get (&proc_cmdline_cached);
-	if (G_UNLIKELY (!proc_cmdline)) {
-		gs_free char *str = NULL;
+    proc_cmdline = g_atomic_pointer_get(&proc_cmdline_cached);
+    if (G_UNLIKELY(!proc_cmdline)) {
+        gs_free char *str = NULL;
 
-		g_file_get_contents ("/proc/cmdline", &str, NULL, NULL);
-		str = nm_str_realloc (str);
+        g_file_get_contents("/proc/cmdline", &str, NULL, NULL);
+        str = nm_str_realloc(str);
 
-		proc_cmdline = str ?: "";
-		if (!g_atomic_pointer_compare_and_exchange (&proc_cmdline_cached, NULL, proc_cmdline))
-			goto again;
+        proc_cmdline = str ?: "";
+        if (!g_atomic_pointer_compare_and_exchange(&proc_cmdline_cached, NULL, proc_cmdline))
+            goto again;
 
-		g_steal_pointer (&str);
-	}
+        g_steal_pointer(&str);
+    }
 
-	return proc_cmdline;
+    return proc_cmdline;
 }
 
-const char *const*
-nm_utils_proc_cmdline_split (void)
+const char *const *
+nm_utils_proc_cmdline_split(void)
 {
-	static const char *const*volatile proc_cmdline_cached = NULL;
-	const char *const*proc_cmdline;
+    static const char *const *volatile proc_cmdline_cached = NULL;
+    const char *const *proc_cmdline;
 
 again:
-	proc_cmdline = g_atomic_pointer_get (&proc_cmdline_cached);
-	if (G_UNLIKELY (!proc_cmdline)) {
-		gs_strfreev char **split = NULL;
+    proc_cmdline = g_atomic_pointer_get(&proc_cmdline_cached);
+    if (G_UNLIKELY(!proc_cmdline)) {
+        gs_strfreev char **split = NULL;
 
-		split = nm_utils_strsplit_quoted (nm_utils_proc_cmdline ());
-		if (!g_atomic_pointer_compare_and_exchange (&proc_cmdline_cached, NULL, (gpointer) split))
-			goto again;
+        split = nm_utils_strsplit_quoted(nm_utils_proc_cmdline());
+        if (!g_atomic_pointer_compare_and_exchange(&proc_cmdline_cached, NULL, (gpointer) split))
+            goto again;
 
-		proc_cmdline = (const char *const*) g_steal_pointer (&split);
-	}
+        proc_cmdline = (const char *const *) g_steal_pointer(&split);
+    }
 
-	return proc_cmdline;
+    return proc_cmdline;
 }
 
 /*****************************************************************************/
@@ -2930,94 +3243,88 @@ again:
  *
  * Returns: the arp-type or negative value on error. */
 int
-nm_utils_arp_type_detect_from_hwaddrlen (gsize hwaddr_len)
+nm_utils_arp_type_detect_from_hwaddrlen(gsize hwaddr_len)
 {
-	switch (hwaddr_len) {
-	case ETH_ALEN:
-		return ARPHRD_ETHER;
-	case INFINIBAND_ALEN:
-		return ARPHRD_INFINIBAND;
-	default:
-		/* Note: if you ever support anything but ethernet and infiniband,
-		 * make sure to look at all callers. They assert that it's one of
-		 * these two. */
-		return -EINVAL;
-	}
+    switch (hwaddr_len) {
+    case ETH_ALEN:
+        return ARPHRD_ETHER;
+    case INFINIBAND_ALEN:
+        return ARPHRD_INFINIBAND;
+    default:
+        /* Note: if you ever support anything but ethernet and infiniband,
+         * make sure to look at all callers. They assert that it's one of
+         * these two. */
+        return -EINVAL;
+    }
 }
 
 gboolean
-nm_utils_arp_type_validate_hwaddr (int arp_type,
-                                   const guint8 *hwaddr,
-                                   gsize hwaddr_len)
+nm_utils_arp_type_validate_hwaddr(int arp_type, const guint8 *hwaddr, gsize hwaddr_len)
 {
-
-	if (!hwaddr)
-		return FALSE;
-
-	if (arp_type == ARPHRD_ETHER) {
-		G_STATIC_ASSERT (ARPHRD_ETHER >= 0 && ARPHRD_ETHER <= 0xFF);
-		if (hwaddr_len != ETH_ALEN)
-			return FALSE;
-	} else if (arp_type == ARPHRD_INFINIBAND) {
-		G_STATIC_ASSERT (ARPHRD_INFINIBAND >= 0 && ARPHRD_INFINIBAND <= 0xFF);
-		if (hwaddr_len != INFINIBAND_ALEN)
-			return FALSE;
-	} else
-		return FALSE;
-
-	nm_assert (arp_type == nm_utils_arp_type_detect_from_hwaddrlen (hwaddr_len));
-	return TRUE;
+    if (!hwaddr)
+        return FALSE;
+
+    if (arp_type == ARPHRD_ETHER) {
+        G_STATIC_ASSERT(ARPHRD_ETHER >= 0 && ARPHRD_ETHER <= 0xFF);
+        if (hwaddr_len != ETH_ALEN)
+            return FALSE;
+    } else if (arp_type == ARPHRD_INFINIBAND) {
+        G_STATIC_ASSERT(ARPHRD_INFINIBAND >= 0 && ARPHRD_INFINIBAND <= 0xFF);
+        if (hwaddr_len != INFINIBAND_ALEN)
+            return FALSE;
+    } else
+        return FALSE;
+
+    nm_assert(arp_type == nm_utils_arp_type_detect_from_hwaddrlen(hwaddr_len));
+    return TRUE;
 }
 
 gboolean
-nm_utils_arp_type_get_hwaddr_relevant_part (int arp_type,
-                                            const guint8 **hwaddr,
-                                            gsize *hwaddr_len)
+nm_utils_arp_type_get_hwaddr_relevant_part(int arp_type, const guint8 **hwaddr, gsize *hwaddr_len)
 {
-	g_return_val_if_fail (   hwaddr
-	                      && hwaddr_len
-	                      && nm_utils_arp_type_validate_hwaddr (arp_type, *hwaddr, *hwaddr_len),
-	                      FALSE);
-
-	/* for infiniband, we only consider the last 8 bytes. */
-	if (arp_type == ARPHRD_INFINIBAND) {
-		*hwaddr += (INFINIBAND_ALEN - 8);
-		*hwaddr_len = 8;
-	}
-
-	return TRUE;
+    g_return_val_if_fail(hwaddr && hwaddr_len
+                             && nm_utils_arp_type_validate_hwaddr(arp_type, *hwaddr, *hwaddr_len),
+                         FALSE);
+
+    /* for infiniband, we only consider the last 8 bytes. */
+    if (arp_type == ARPHRD_INFINIBAND) {
+        *hwaddr += (INFINIBAND_ALEN - 8);
+        *hwaddr_len = 8;
+    }
+
+    return TRUE;
 }
 
 /*****************************************************************************/
 
 /* Returns the "u" (universal/local) bit value for a Modified EUI-64 */
 static gboolean
-get_gre_eui64_u_bit (guint32 addr)
+get_gre_eui64_u_bit(guint32 addr)
 {
-	static const struct {
-		guint32 mask;
-		guint32 result;
-	} items[] = {
-		{ 0xff000000 }, { 0x7f000000 },  /* IPv4 loopback */
-		{ 0xf0000000 }, { 0xe0000000 },  /* IPv4 multicast */
-		{ 0xffffff00 }, { 0xe0000000 },  /* IPv4 local multicast */
-		{ 0xffffffff }, { INADDR_BROADCAST },  /* limited broadcast */
-		{ 0xff000000 }, { 0x00000000 },  /* zero net */
-		{ 0xff000000 }, { 0x0a000000 },  /* private 10 (RFC3330) */
-		{ 0xfff00000 }, { 0xac100000 },  /* private 172 */
-		{ 0xffff0000 }, { 0xc0a80000 },  /* private 192 */
-		{ 0xffff0000 }, { 0xa9fe0000 },  /* IPv4 link-local */
-		{ 0xffffff00 }, { 0xc0586300 },  /* anycast 6-to-4 */
-		{ 0xffffff00 }, { 0xc0000200 },  /* test 192 */
-		{ 0xfffe0000 }, { 0xc6120000 },  /* test 198 */
-	};
-	guint i;
-
-	for (i = 0; i < G_N_ELEMENTS (items); i++) {
-		if ((addr & htonl (items[i].mask)) == htonl (items[i].result))
-			return 0x00; /* "local" scope */
-	}
-	return 0x02; /* "universal" scope */
+    static const struct {
+        guint32 mask;
+        guint32 result;
+    } items[] = {
+        {0xff000000}, {0x7f000000},       /* IPv4 loopback */
+        {0xf0000000}, {0xe0000000},       /* IPv4 multicast */
+        {0xffffff00}, {0xe0000000},       /* IPv4 local multicast */
+        {0xffffffff}, {INADDR_BROADCAST}, /* limited broadcast */
+        {0xff000000}, {0x00000000},       /* zero net */
+        {0xff000000}, {0x0a000000},       /* private 10 (RFC3330) */
+        {0xfff00000}, {0xac100000},       /* private 172 */
+        {0xffff0000}, {0xc0a80000},       /* private 192 */
+        {0xffff0000}, {0xa9fe0000},       /* IPv4 link-local */
+        {0xffffff00}, {0xc0586300},       /* anycast 6-to-4 */
+        {0xffffff00}, {0xc0000200},       /* test 192 */
+        {0xfffe0000}, {0xc6120000},       /* test 198 */
+    };
+    guint i;
+
+    for (i = 0; i < G_N_ELEMENTS(items); i++) {
+        if ((addr & htonl(items[i].mask)) == htonl(items[i].result))
+            return 0x00; /* "local" scope */
+    }
+    return 0x02; /* "universal" scope */
 }
 
 /**
@@ -3037,70 +3344,70 @@ get_gre_eui64_u_bit (guint32 addr)
  * if could not be constructed.
  */
 gboolean
-nm_utils_get_ipv6_interface_identifier (NMLinkType link_type,
-                                        const guint8 *hwaddr,
-                                        guint hwaddr_len,
-                                        guint dev_id,
-                                        NMUtilsIPv6IfaceId *out_iid)
+nm_utils_get_ipv6_interface_identifier(NMLinkType          link_type,
+                                       const guint8 *      hwaddr,
+                                       guint               hwaddr_len,
+                                       guint               dev_id,
+                                       NMUtilsIPv6IfaceId *out_iid)
 {
-	guint32 addr;
-
-	g_return_val_if_fail (hwaddr != NULL, FALSE);
-	g_return_val_if_fail (hwaddr_len > 0, FALSE);
-	g_return_val_if_fail (out_iid != NULL, FALSE);
-
-	out_iid->id = 0;
-
-	switch (link_type) {
-	case NM_LINK_TYPE_INFINIBAND:
-		/* Use the port GUID per http://tools.ietf.org/html/rfc4391#section-8,
-		 * making sure to set the 'u' bit to 1.  The GUID is the lower 64 bits
-		 * of the IPoIB interface's hardware address.
-		 */
-		g_return_val_if_fail (hwaddr_len == INFINIBAND_ALEN, FALSE);
-		memcpy (out_iid->id_u8, hwaddr + INFINIBAND_ALEN - 8, 8);
-		out_iid->id_u8[0] |= 0x02;
-		return TRUE;
-	case NM_LINK_TYPE_GRE:
-		/* Hardware address is the network-endian IPv4 address */
-		g_return_val_if_fail (hwaddr_len == 4, FALSE);
-		addr = * (guint32 *) hwaddr;
-		out_iid->id_u8[0] = get_gre_eui64_u_bit (addr);
-		out_iid->id_u8[1] = 0x00;
-		out_iid->id_u8[2] = 0x5E;
-		out_iid->id_u8[3] = 0xFE;
-		memcpy (out_iid->id_u8 + 4, &addr, 4);
-		return TRUE;
-	case NM_LINK_TYPE_6LOWPAN:
-		/* The hardware address is already 64-bit. This is the case for
-		* IEEE 802.15.4 networks. */
-		memcpy (out_iid->id_u8, hwaddr, sizeof (out_iid->id_u8));
-		return TRUE;
-	default:
-		if (hwaddr_len == ETH_ALEN) {
-			/* Translate 48-bit MAC address to a 64-bit Modified EUI-64.  See
-			 * http://tools.ietf.org/html/rfc4291#appendix-A and the Linux
-			 * kernel's net/ipv6/addrconf.c::ipv6_generate_eui64() function.
-			 */
-			out_iid->id_u8[0] = hwaddr[0];
-			out_iid->id_u8[1] = hwaddr[1];
-			out_iid->id_u8[2] = hwaddr[2];
-			if (dev_id) {
-				out_iid->id_u8[3] = (dev_id >> 8) & 0xff;
-				out_iid->id_u8[4] = dev_id & 0xff;
-			} else {
-				out_iid->id_u8[0] ^= 0x02;
-				out_iid->id_u8[3] = 0xff;
-				out_iid->id_u8[4] = 0xfe;
-			}
-			out_iid->id_u8[5] = hwaddr[3];
-			out_iid->id_u8[6] = hwaddr[4];
-			out_iid->id_u8[7] = hwaddr[5];
-			return TRUE;
-		}
-		break;
-	}
-	return FALSE;
+    guint32 addr;
+
+    g_return_val_if_fail(hwaddr != NULL, FALSE);
+    g_return_val_if_fail(hwaddr_len > 0, FALSE);
+    g_return_val_if_fail(out_iid != NULL, FALSE);
+
+    out_iid->id = 0;
+
+    switch (link_type) {
+    case NM_LINK_TYPE_INFINIBAND:
+        /* Use the port GUID per http://tools.ietf.org/html/rfc4391#section-8,
+         * making sure to set the 'u' bit to 1.  The GUID is the lower 64 bits
+         * of the IPoIB interface's hardware address.
+         */
+        g_return_val_if_fail(hwaddr_len == INFINIBAND_ALEN, FALSE);
+        memcpy(out_iid->id_u8, hwaddr + INFINIBAND_ALEN - 8, 8);
+        out_iid->id_u8[0] |= 0x02;
+        return TRUE;
+    case NM_LINK_TYPE_GRE:
+        /* Hardware address is the network-endian IPv4 address */
+        g_return_val_if_fail(hwaddr_len == 4, FALSE);
+        addr              = *(guint32 *) hwaddr;
+        out_iid->id_u8[0] = get_gre_eui64_u_bit(addr);
+        out_iid->id_u8[1] = 0x00;
+        out_iid->id_u8[2] = 0x5E;
+        out_iid->id_u8[3] = 0xFE;
+        memcpy(out_iid->id_u8 + 4, &addr, 4);
+        return TRUE;
+    case NM_LINK_TYPE_6LOWPAN:
+        /* The hardware address is already 64-bit. This is the case for
+         * IEEE 802.15.4 networks. */
+        memcpy(out_iid->id_u8, hwaddr, sizeof(out_iid->id_u8));
+        return TRUE;
+    default:
+        if (hwaddr_len == ETH_ALEN) {
+            /* Translate 48-bit MAC address to a 64-bit Modified EUI-64.  See
+             * http://tools.ietf.org/html/rfc4291#appendix-A and the Linux
+             * kernel's net/ipv6/addrconf.c::ipv6_generate_eui64() function.
+             */
+            out_iid->id_u8[0] = hwaddr[0];
+            out_iid->id_u8[1] = hwaddr[1];
+            out_iid->id_u8[2] = hwaddr[2];
+            if (dev_id) {
+                out_iid->id_u8[3] = (dev_id >> 8) & 0xff;
+                out_iid->id_u8[4] = dev_id & 0xff;
+            } else {
+                out_iid->id_u8[0] ^= 0x02;
+                out_iid->id_u8[3] = 0xff;
+                out_iid->id_u8[4] = 0xfe;
+            }
+            out_iid->id_u8[5] = hwaddr[3];
+            out_iid->id_u8[6] = hwaddr[4];
+            out_iid->id_u8[7] = hwaddr[5];
+            return TRUE;
+        }
+        break;
+    }
+    return FALSE;
 }
 
 /*****************************************************************************/
@@ -3116,10 +3423,9 @@ nm_utils_get_ipv6_interface_identifier (NMLinkType link_type,
  * token.
  */
 void
-nm_utils_ipv6_addr_set_interface_identifier (struct in6_addr *addr,
-                                            const NMUtilsIPv6IfaceId iid)
+nm_utils_ipv6_addr_set_interface_identifier(struct in6_addr *addr, const NMUtilsIPv6IfaceId iid)
 {
-	memcpy (addr->s6_addr + 8, &iid.id_u8, 8);
+    memcpy(addr->s6_addr + 8, &iid.id_u8, 8);
 }
 
 /**
@@ -3131,10 +3437,10 @@ nm_utils_ipv6_addr_set_interface_identifier (struct in6_addr *addr,
  * the interface identifier.
  */
 void
-nm_utils_ipv6_interface_identifier_get_from_addr (NMUtilsIPv6IfaceId *iid,
+nm_utils_ipv6_interface_identifier_get_from_addr(NMUtilsIPv6IfaceId *   iid,
                                                  const struct in6_addr *addr)
 {
-	memcpy (iid, addr->s6_addr + 8, 8);
+    memcpy(iid, addr->s6_addr + 8, 8);
 }
 
 /**
@@ -3148,21 +3454,20 @@ nm_utils_ipv6_interface_identifier_get_from_addr (NMUtilsIPv6IfaceId *iid,
  * Returns: %TRUE if the @token is a valid token, %FALSE otherwise
  */
 gboolean
-nm_utils_ipv6_interface_identifier_get_from_token (NMUtilsIPv6IfaceId *iid,
-                                                   const char *token)
+nm_utils_ipv6_interface_identifier_get_from_token(NMUtilsIPv6IfaceId *iid, const char *token)
 {
-	struct in6_addr i6_token;
+    struct in6_addr i6_token;
 
-	g_return_val_if_fail (token, FALSE);
+    g_return_val_if_fail(token, FALSE);
 
-	if (!inet_pton (AF_INET6, token, &i6_token))
-		return FALSE;
+    if (!inet_pton(AF_INET6, token, &i6_token))
+        return FALSE;
 
-	if (!_nm_utils_inet6_is_token (&i6_token))
-		return FALSE;
+    if (!_nm_utils_inet6_is_token(&i6_token))
+        return FALSE;
 
-	nm_utils_ipv6_interface_identifier_get_from_addr (iid, &i6_token);
-	return TRUE;
+    nm_utils_ipv6_interface_identifier_get_from_addr(iid, &i6_token);
+    return TRUE;
 }
 
 /**
@@ -3176,291 +3481,299 @@ nm_utils_ipv6_interface_identifier_get_from_token (NMUtilsIPv6IfaceId *iid,
  * Returns: the input buffer filled with the id as string.
  */
 const char *
-nm_utils_inet6_interface_identifier_to_token (NMUtilsIPv6IfaceId iid,
-                                              char buf[static INET6_ADDRSTRLEN])
+nm_utils_inet6_interface_identifier_to_token(NMUtilsIPv6IfaceId iid,
+                                             char               buf[static INET6_ADDRSTRLEN])
 {
-	struct in6_addr i6_token = { .s6_addr = { 0, } };
+    struct in6_addr i6_token = {.s6_addr = {
+                                    0,
+                                }};
 
-	nm_assert (buf);
-	nm_utils_ipv6_addr_set_interface_identifier (&i6_token, iid);
-	return _nm_utils_inet6_ntop (&i6_token, buf);
+    nm_assert(buf);
+    nm_utils_ipv6_addr_set_interface_identifier(&i6_token, iid);
+    return _nm_utils_inet6_ntop(&i6_token, buf);
 }
 
 /*****************************************************************************/
 
 char *
-nm_utils_stable_id_random (void)
+nm_utils_stable_id_random(void)
 {
-	char buf[15];
+    char buf[15];
 
-	nm_utils_random_bytes (buf, sizeof (buf));
-	return g_base64_encode ((guchar *) buf, sizeof (buf));
+    nm_utils_random_bytes(buf, sizeof(buf));
+    return g_base64_encode((guchar *) buf, sizeof(buf));
 }
 
 char *
-nm_utils_stable_id_generated_complete (const char *stable_id_generated)
+nm_utils_stable_id_generated_complete(const char *stable_id_generated)
 {
-	nm_auto_free_checksum GChecksum *sum = NULL;
-	guint8 buf[NM_UTILS_CHECKSUM_LENGTH_SHA1];
-	char *base64;
+    nm_auto_free_checksum GChecksum *sum = NULL;
+    guint8                           buf[NM_UTILS_CHECKSUM_LENGTH_SHA1];
+    char *                           base64;
 
-	/* for NM_UTILS_STABLE_TYPE_GENERATED we generate a possibly long string
-	 * by doing text-substitutions in nm_utils_stable_id_parse().
-	 *
-	 * Let's shorten the (possibly) long stable_id to something more compact. */
+    /* for NM_UTILS_STABLE_TYPE_GENERATED we generate a possibly long string
+     * by doing text-substitutions in nm_utils_stable_id_parse().
+     *
+     * Let's shorten the (possibly) long stable_id to something more compact. */
 
-	g_return_val_if_fail (stable_id_generated, NULL);
+    g_return_val_if_fail(stable_id_generated, NULL);
 
-	sum = g_checksum_new (G_CHECKSUM_SHA1);
-	g_checksum_update (sum, (guchar *) stable_id_generated, strlen (stable_id_generated));
-	nm_utils_checksum_get_digest (sum, buf);
+    sum = g_checksum_new(G_CHECKSUM_SHA1);
+    g_checksum_update(sum, (guchar *) stable_id_generated, strlen(stable_id_generated));
+    nm_utils_checksum_get_digest(sum, buf);
 
-	/* we don't care to use the sha1 sum in common hex representation.
-	 * Use instead base64, it's 27 chars (stripping the padding) vs.
-	 * 40. */
+    /* we don't care to use the sha1 sum in common hex representation.
+     * Use instead base64, it's 27 chars (stripping the padding) vs.
+     * 40. */
 
-	base64 = g_base64_encode ((guchar *) buf, sizeof (buf));
-	nm_assert (strlen (base64) == 28);
-	nm_assert (base64[27] == '=');
+    base64 = g_base64_encode((guchar *) buf, sizeof(buf));
+    nm_assert(strlen(base64) == 28);
+    nm_assert(base64[27] == '=');
 
-	base64[27] = '\0';
-	return base64;
+    base64[27] = '\0';
+    return base64;
 }
 
 static void
-_stable_id_append (GString *str,
-                   const char *substitution)
+_stable_id_append(GString *str, const char *substitution)
 {
-	if (!substitution)
-		substitution = "";
-	g_string_append_printf (str, "=%zu{%s}", strlen (substitution), substitution);
+    if (!substitution)
+        substitution = "";
+    g_string_append_printf(str, "=%zu{%s}", strlen(substitution), substitution);
 }
 
 NMUtilsStableType
-nm_utils_stable_id_parse (const char *stable_id,
-                          const char *deviceid,
-                          const char *hwaddr,
-                          const char *bootid,
-                          const char *uuid,
-                          char **out_generated)
+nm_utils_stable_id_parse(const char *stable_id,
+                         const char *deviceid,
+                         const char *hwaddr,
+                         const char *bootid,
+                         const char *uuid,
+                         char **     out_generated)
 {
-	gsize i, idx_start;
-	GString *str = NULL;
-
-	g_return_val_if_fail (out_generated, NM_UTILS_STABLE_TYPE_RANDOM);
-
-	if (!stable_id) {
-		*out_generated = NULL;
-		return NM_UTILS_STABLE_TYPE_UUID;
-	}
-
-	/* the stable-id allows for some dynamic by performing text-substitutions
-	 * of ${...} patterns.
-	 *
-	 * At first, it looks a bit like bash parameter substitution.
-	 * In contrast however, the process is unambiguous so that the resulting
-	 * effective id differs if:
-	 *  - the original, untranslated stable-id differs
-	 *  - or any of the subsitutions differs.
-	 *
-	 * The reason for that is, for example if you specify "${CONNECTION}" in the
-	 * stable-id, then the resulting ID should be always(!) unique for this connection.
-	 * There should be no way another connection could specify any stable-id that results
-	 * in the same addresses to be generated (aside hash collisions).
-	 *
-	 *
-	 * For example: say you have a connection with UUID
-	 * "123e4567-e89b-12d3-a456-426655440000" which happens also to be
-	 * the current boot-id.
-	 * Then:
-	 *   (1) connection.stable-id = <NULL>
-	 *   (2) connection.stable-id = "123e4567-e89b-12d3-a456-426655440000"
-	 *   (3) connection.stable-id = "${CONNECTION}"
-	 *   (3) connection.stable-id = "${BOOT}"
-	 * will all generate different addresses, although in one way or the
-	 * other, they all mangle the uuid "123e4567-e89b-12d3-a456-426655440000".
-	 *
-	 * For example, with stable-id="${FOO}${BAR}" the substitutions
-	 *   - FOO="ab", BAR="c"
-	 *   - FOO="a",  BAR="bc"
-	 * should give a different effective id.
-	 *
-	 * For example, with FOO="x" and BAR="x", the stable-ids
-	 *   - "${FOO}${BAR}"
-	 *   - "${BAR}${FOO}"
-	 * should give a different effective id.
-	 */
-
-	idx_start = 0;
-	for (i = 0; stable_id[i]; ) {
-		if (stable_id[i] != '$') {
-			i++;
-			continue;
-		}
-
-#define CHECK_PREFIX(prefix) \
-		({ \
-			gboolean _match = FALSE; \
-			\
-			if (g_str_has_prefix (&stable_id[i], ""prefix"")) { \
-				_match = TRUE; \
-				if (!str) \
-					str = g_string_sized_new (256); \
-				i += NM_STRLEN (prefix); \
-				g_string_append_len (str, &(stable_id)[idx_start], i - idx_start); \
-				idx_start = i; \
-			} \
-			_match; \
-		})
-		if (CHECK_PREFIX ("${CONNECTION}"))
-			_stable_id_append (str, uuid);
-		else if (CHECK_PREFIX ("${BOOT}"))
-			_stable_id_append (str, bootid);
-		else if (CHECK_PREFIX ("${DEVICE}"))
-			_stable_id_append (str, deviceid);
-		else if (CHECK_PREFIX ("${MAC}"))
-			_stable_id_append (str, hwaddr);
-		else if (g_str_has_prefix (&stable_id[i], "${RANDOM}")) {
-			/* RANDOM makes not so much sense for cloned-mac-address
-			 * as the result is similar to specyifing "cloned-mac-address=random".
-			 * It makes however sense for RFC 7217 Stable Privacy IPv6 addresses
-			 * where this is effectively the only way to generate a different
-			 * (random) host identifier for each connect.
-			 *
-			 * With RANDOM, the user can switch the lifetime of the
-			 * generated cloned-mac-address and IPv6 host identifier
-			 * by toggeling only the stable-id property of the connection.
-			 * With RANDOM being the most short-lived, ~non-stable~ variant.
-			 */
-			if (str)
-				g_string_free (str, TRUE);
-			*out_generated = NULL;
-			return NM_UTILS_STABLE_TYPE_RANDOM;
-		} else {
-			/* The text following the '$' is not recognized as valid
-			 * substitution pattern. Treat it verbatim. */
-			i++;
-
-			/* Note that using unrecognized substitution patterns might
-			 * yield different results with future versions. Avoid that,
-			 * by not using '$' (except for actual substitutions) or escape
-			 * it as "$$" (which is guaranteed to be treated verbatim
-			 * in future). */
-			if (stable_id[i] == '$')
-				i++;
-		}
-	}
+    gsize    i, idx_start;
+    GString *str = NULL;
+
+    g_return_val_if_fail(out_generated, NM_UTILS_STABLE_TYPE_RANDOM);
+
+    if (!stable_id) {
+        *out_generated = NULL;
+        return NM_UTILS_STABLE_TYPE_UUID;
+    }
+
+    /* the stable-id allows for some dynamic by performing text-substitutions
+     * of ${...} patterns.
+     *
+     * At first, it looks a bit like bash parameter substitution.
+     * In contrast however, the process is unambiguous so that the resulting
+     * effective id differs if:
+     *  - the original, untranslated stable-id differs
+     *  - or any of the subsitutions differs.
+     *
+     * The reason for that is, for example if you specify "${CONNECTION}" in the
+     * stable-id, then the resulting ID should be always(!) unique for this connection.
+     * There should be no way another connection could specify any stable-id that results
+     * in the same addresses to be generated (aside hash collisions).
+     *
+     *
+     * For example: say you have a connection with UUID
+     * "123e4567-e89b-12d3-a456-426655440000" which happens also to be
+     * the current boot-id.
+     * Then:
+     *   (1) connection.stable-id = <NULL>
+     *   (2) connection.stable-id = "123e4567-e89b-12d3-a456-426655440000"
+     *   (3) connection.stable-id = "${CONNECTION}"
+     *   (3) connection.stable-id = "${BOOT}"
+     * will all generate different addresses, although in one way or the
+     * other, they all mangle the uuid "123e4567-e89b-12d3-a456-426655440000".
+     *
+     * For example, with stable-id="${FOO}${BAR}" the substitutions
+     *   - FOO="ab", BAR="c"
+     *   - FOO="a",  BAR="bc"
+     * should give a different effective id.
+     *
+     * For example, with FOO="x" and BAR="x", the stable-ids
+     *   - "${FOO}${BAR}"
+     *   - "${BAR}${FOO}"
+     * should give a different effective id.
+     */
+
+    idx_start = 0;
+    for (i = 0; stable_id[i];) {
+        if (stable_id[i] != '$') {
+            i++;
+            continue;
+        }
+
+#define CHECK_PREFIX(prefix)                                                  \
+    ({                                                                        \
+        gboolean _match = FALSE;                                              \
+                                                                              \
+        if (g_str_has_prefix(&stable_id[i], "" prefix "")) {                  \
+            _match = TRUE;                                                    \
+            if (!str)                                                         \
+                str = g_string_sized_new(256);                                \
+            i += NM_STRLEN(prefix);                                           \
+            g_string_append_len(str, &(stable_id)[idx_start], i - idx_start); \
+            idx_start = i;                                                    \
+        }                                                                     \
+        _match;                                                               \
+    })
+        if (CHECK_PREFIX("${CONNECTION}"))
+            _stable_id_append(str, uuid);
+        else if (CHECK_PREFIX("${BOOT}"))
+            _stable_id_append(str, bootid);
+        else if (CHECK_PREFIX("${DEVICE}"))
+            _stable_id_append(str, deviceid);
+        else if (CHECK_PREFIX("${MAC}"))
+            _stable_id_append(str, hwaddr);
+        else if (g_str_has_prefix(&stable_id[i], "${RANDOM}")) {
+            /* RANDOM makes not so much sense for cloned-mac-address
+             * as the result is similar to specifying "cloned-mac-address=random".
+             * It makes however sense for RFC 7217 Stable Privacy IPv6 addresses
+             * where this is effectively the only way to generate a different
+             * (random) host identifier for each connect.
+             *
+             * With RANDOM, the user can switch the lifetime of the
+             * generated cloned-mac-address and IPv6 host identifier
+             * by toggling only the stable-id property of the connection.
+             * With RANDOM being the most short-lived, ~non-stable~ variant.
+             */
+            if (str)
+                g_string_free(str, TRUE);
+            *out_generated = NULL;
+            return NM_UTILS_STABLE_TYPE_RANDOM;
+        } else {
+            /* The text following the '$' is not recognized as valid
+             * substitution pattern. Treat it verbatim. */
+            i++;
+
+            /* Note that using unrecognized substitution patterns might
+             * yield different results with future versions. Avoid that,
+             * by not using '$' (except for actual substitutions) or escape
+             * it as "$$" (which is guaranteed to be treated verbatim
+             * in future). */
+            if (stable_id[i] == '$')
+                i++;
+        }
+    }
 #undef CHECK_PREFIX
 
-	if (!str) {
-		*out_generated = NULL;
-		return NM_UTILS_STABLE_TYPE_STABLE_ID;
-	}
+    if (!str) {
+        *out_generated = NULL;
+        return NM_UTILS_STABLE_TYPE_STABLE_ID;
+    }
 
-	if (idx_start < i)
-		g_string_append_len (str, &stable_id[idx_start], i - idx_start);
-	*out_generated = g_string_free (str, FALSE);
-	return NM_UTILS_STABLE_TYPE_GENERATED;
+    if (idx_start < i)
+        g_string_append_len(str, &stable_id[idx_start], i - idx_start);
+    *out_generated = g_string_free(str, FALSE);
+    return NM_UTILS_STABLE_TYPE_GENERATED;
 }
 
 /*****************************************************************************/
 
 static gboolean
-_is_reserved_ipv6_iid (const guint8 *iid)
+_is_reserved_ipv6_iid(const guint8 *iid)
 {
-	/* https://tools.ietf.org/html/rfc5453 */
-	/* https://www.iana.org/assignments/ipv6-interface-ids/ipv6-interface-ids.xml */
-
-	/* 0000:0000:0000:0000 (Subnet-Router Anycast [RFC4291]) */
-	if (memcmp (iid, &nm_ip_addr_zero.addr6.s6_addr[8], 8) == 0)
-		return TRUE;
-
-	/* 0200:5EFF:FE00:0000 - 0200:5EFF:FE00:5212 (Reserved IPv6 Interface Identifiers corresponding to the IANA Ethernet Block [RFC4291])
-	 * 0200:5EFF:FE00:5213                       (Proxy Mobile IPv6 [RFC6543])
-	 * 0200:5EFF:FE00:5214 - 0200:5EFF:FEFF:FFFF (Reserved IPv6 Interface Identifiers corresponding to the IANA Ethernet Block [RFC4291]) */
-	if (memcmp (iid, (const guint8[]) { 0x02, 0x00, 0x5E, 0xFF, 0xFE }, 5) == 0)
-		return TRUE;
-
-	/* FDFF:FFFF:FFFF:FF80 - FDFF:FFFF:FFFF:FFFF (Reserved Subnet Anycast Addresses [RFC2526]) */
-	if (memcmp (iid, (const guint8[]) { 0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }, 7) == 0) {
-		if (iid[7] & 0x80)
-			return TRUE;
-	}
-
-	return FALSE;
+    /* https://tools.ietf.org/html/rfc5453 */
+    /* https://www.iana.org/assignments/ipv6-interface-ids/ipv6-interface-ids.xml */
+
+    /* 0000:0000:0000:0000 (Subnet-Router Anycast [RFC4291]) */
+    if (memcmp(iid, &nm_ip_addr_zero.addr6.s6_addr[8], 8) == 0)
+        return TRUE;
+
+    /* 0200:5EFF:FE00:0000 - 0200:5EFF:FE00:5212 (Reserved IPv6 Interface Identifiers corresponding to the IANA Ethernet Block [RFC4291])
+     * 0200:5EFF:FE00:5213                       (Proxy Mobile IPv6 [RFC6543])
+     * 0200:5EFF:FE00:5214 - 0200:5EFF:FEFF:FFFF (Reserved IPv6 Interface Identifiers corresponding to the IANA Ethernet Block [RFC4291]) */
+    if (memcmp(iid, (const guint8[]){0x02, 0x00, 0x5E, 0xFF, 0xFE}, 5) == 0)
+        return TRUE;
+
+    /* FDFF:FFFF:FFFF:FF80 - FDFF:FFFF:FFFF:FFFF (Reserved Subnet Anycast Addresses [RFC2526]) */
+    if (memcmp(iid, (const guint8[]){0xFD, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}, 7) == 0) {
+        if (iid[7] & 0x80)
+            return TRUE;
+    }
+
+    return FALSE;
 }
 
 static gboolean
-_set_stable_privacy (NMUtilsStableType stable_type,
-                     struct in6_addr *addr,
-                     const char *ifname,
-                     const char *network_id,
-                     guint32 dad_counter,
-                     const guint8 *host_id,
-                     gsize host_id_len,
-                     GError **error)
+_set_stable_privacy(NMUtilsStableType stable_type,
+                    struct in6_addr * addr,
+                    const char *      ifname,
+                    const char *      network_id,
+                    guint32           dad_counter,
+                    const guint8 *    host_id,
+                    gsize             host_id_len,
+                    GError **         error)
 {
-	nm_auto_free_checksum GChecksum *sum = NULL;
-	guint8 digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
-	guint32 tmp[2];
-
-	nm_assert (host_id_len);
-	nm_assert (network_id);
-
-	sum = g_checksum_new (G_CHECKSUM_SHA256);
-
-	host_id_len = MIN (host_id_len, G_MAXUINT32);
-
-	if (stable_type != NM_UTILS_STABLE_TYPE_UUID) {
-		guint8 stable_type_uint8;
-
-		nm_assert (stable_type < (NMUtilsStableType) 255);
-		stable_type_uint8 = (guint8) stable_type;
-
-		/* Preferably, we would always like to include the stable-type,
-		 * but for backward compatibility reasons, we cannot for UUID.
-		 *
-		 * That is no real problem and it is still impossible to
-		 * force a collision here, because of how the remaining
-		 * fields are hashed. That is, as we also hash @host_id_len
-		 * and the terminating '\0' of @network_id, it is unambigiously
-		 * possible to revert the process and deduce the @stable_type.
-		 */
-		g_checksum_update (sum, &stable_type_uint8, sizeof (stable_type_uint8));
-	}
-
-	g_checksum_update (sum, addr->s6_addr, 8);
-	g_checksum_update (sum, (const guchar *) ifname, strlen (ifname) + 1);
-	g_checksum_update (sum, (const guchar *) network_id, strlen (network_id) + 1);
-	tmp[0] = htonl (dad_counter);
-	tmp[1] = htonl (host_id_len);
-	g_checksum_update (sum, (const guchar *) tmp, sizeof (tmp));
-	g_checksum_update (sum, (const guchar *) host_id, host_id_len);
-	nm_utils_checksum_get_digest (sum, digest);
-
-	while (_is_reserved_ipv6_iid (digest)) {
-		g_checksum_reset (sum);
-		tmp[0] = htonl (++dad_counter);
-		g_checksum_update (sum, digest, sizeof (digest));
-		g_checksum_update (sum, (const guchar *) &tmp[0], sizeof (tmp[0]));
-		nm_utils_checksum_get_digest (sum, digest);
-	}
-
-	memcpy (addr->s6_addr + 8, &digest[0], 8);
-	return TRUE;
+    nm_auto_free_checksum GChecksum *sum = NULL;
+    guint8                           digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
+    guint32                          tmp[2];
+
+    nm_assert(host_id_len);
+    nm_assert(network_id);
+
+    sum = g_checksum_new(G_CHECKSUM_SHA256);
+
+    host_id_len = MIN(host_id_len, G_MAXUINT32);
+
+    if (stable_type != NM_UTILS_STABLE_TYPE_UUID) {
+        guint8 stable_type_uint8;
+
+        nm_assert(stable_type < (NMUtilsStableType) 255);
+        stable_type_uint8 = (guint8) stable_type;
+
+        /* Preferably, we would always like to include the stable-type,
+         * but for backward compatibility reasons, we cannot for UUID.
+         *
+         * That is no real problem and it is still impossible to
+         * force a collision here, because of how the remaining
+         * fields are hashed. That is, as we also hash @host_id_len
+         * and the terminating '\0' of @network_id, it is unambiguously
+         * possible to revert the process and deduce the @stable_type.
+         */
+        g_checksum_update(sum, &stable_type_uint8, sizeof(stable_type_uint8));
+    }
+
+    g_checksum_update(sum, addr->s6_addr, 8);
+    g_checksum_update(sum, (const guchar *) ifname, strlen(ifname) + 1);
+    g_checksum_update(sum, (const guchar *) network_id, strlen(network_id) + 1);
+    tmp[0] = htonl(dad_counter);
+    tmp[1] = htonl(host_id_len);
+    g_checksum_update(sum, (const guchar *) tmp, sizeof(tmp));
+    g_checksum_update(sum, (const guchar *) host_id, host_id_len);
+    nm_utils_checksum_get_digest(sum, digest);
+
+    while (_is_reserved_ipv6_iid(digest)) {
+        g_checksum_reset(sum);
+        tmp[0] = htonl(++dad_counter);
+        g_checksum_update(sum, digest, sizeof(digest));
+        g_checksum_update(sum, (const guchar *) &tmp[0], sizeof(tmp[0]));
+        nm_utils_checksum_get_digest(sum, digest);
+    }
+
+    memcpy(addr->s6_addr + 8, &digest[0], 8);
+    return TRUE;
 }
 
 gboolean
-nm_utils_ipv6_addr_set_stable_privacy_impl (NMUtilsStableType stable_type,
-                                            struct in6_addr *addr,
-                                            const char *ifname,
-                                            const char *network_id,
-                                            guint32 dad_counter,
-                                            guint8 *host_id,
-                                            gsize host_id_len,
-                                            GError **error)
+nm_utils_ipv6_addr_set_stable_privacy_impl(NMUtilsStableType stable_type,
+                                           struct in6_addr * addr,
+                                           const char *      ifname,
+                                           const char *      network_id,
+                                           guint32           dad_counter,
+                                           guint8 *          host_id,
+                                           gsize             host_id_len,
+                                           GError **         error)
 {
-	return _set_stable_privacy (stable_type, addr, ifname, network_id, dad_counter, host_id, host_id_len, error);
+    return _set_stable_privacy(stable_type,
+                               addr,
+                               ifname,
+                               network_id,
+                               dad_counter,
+                               host_id,
+                               host_id_len,
+                               error);
 }
 
 #define RFC7217_IDGEN_RETRIES 3
@@ -3473,190 +3786,218 @@ nm_utils_ipv6_addr_set_stable_privacy_impl (NMUtilsStableType stable_type,
  * Returns: %TRUE on success, %FALSE if the address could not be generated.
  */
 gboolean
-nm_utils_ipv6_addr_set_stable_privacy (NMUtilsStableType stable_type,
-                                       struct in6_addr *addr,
-                                       const char *ifname,
-                                       const char *network_id,
-                                       guint32 dad_counter,
-                                       GError **error)
+nm_utils_ipv6_addr_set_stable_privacy(NMUtilsStableType stable_type,
+                                      struct in6_addr * addr,
+                                      const char *      ifname,
+                                      const char *      network_id,
+                                      guint32           dad_counter,
+                                      GError **         error)
 {
-	const guint8 *host_id;
-	gsize host_id_len;
-
-	g_return_val_if_fail (network_id, FALSE);
-
-	if (dad_counter >= RFC7217_IDGEN_RETRIES) {
-		g_set_error_literal (error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
-		                     "Too many DAD collisions");
-		return FALSE;
-	}
-
-	nm_utils_host_id_get (&host_id, &host_id_len);
-
-	return _set_stable_privacy (stable_type, addr, ifname, network_id, dad_counter,
-	                            host_id, host_id_len, error);
+    const guint8 *host_id;
+    gsize         host_id_len;
+
+    g_return_val_if_fail(network_id, FALSE);
+
+    if (dad_counter >= RFC7217_IDGEN_RETRIES) {
+        g_set_error_literal(error,
+                            NM_UTILS_ERROR,
+                            NM_UTILS_ERROR_UNKNOWN,
+                            "Too many DAD collisions");
+        return FALSE;
+    }
+
+    nm_utils_host_id_get(&host_id, &host_id_len);
+
+    return _set_stable_privacy(stable_type,
+                               addr,
+                               ifname,
+                               network_id,
+                               dad_counter,
+                               host_id,
+                               host_id_len,
+                               error);
 }
 
 /*****************************************************************************/
 
 static void
-_hw_addr_eth_complete (struct ether_addr *addr,
-                       const char *current_mac_address,
-                       const char *generate_mac_address_mask)
+_hw_addr_eth_complete(struct ether_addr *addr,
+                      const char *       current_mac_address,
+                      const char *       generate_mac_address_mask)
 {
-	struct ether_addr mask;
-	struct ether_addr oui;
-	struct ether_addr *ouis;
-	gsize ouis_len;
-	guint i;
-
-	/* the second LSB of the first octet means
-	 * "globally unique, OUI enforced, BIA (burned-in-address)"
-	 * vs. "locally-administered". By default, set it to
-	 * generate locally-administered addresses.
-	 *
-	 * Maybe be overwritten by a mask below. */
-	addr->ether_addr_octet[0] |= 2;
-
-	if (!generate_mac_address_mask || !*generate_mac_address_mask)
-		goto out;
-	if (!_nm_utils_generate_mac_address_mask_parse (generate_mac_address_mask,
-	                                                &mask,
-	                                                &ouis,
-	                                                &ouis_len,
-	                                                NULL))
-		goto out;
-
-	nm_assert ((ouis == NULL) ^ (ouis_len != 0));
-	if (ouis) {
-		/* g_random_int() is good enough here. It uses a static GRand instance
-		 * that is seeded from /dev/urandom. */
-		oui = ouis[g_random_int () % ouis_len];
-		g_free (ouis);
-	} else {
-		if (!nm_utils_hwaddr_aton (current_mac_address, &oui, ETH_ALEN))
-			goto out;
-	}
-
-	for (i = 0; i < ETH_ALEN; i++) {
-		const guint8 a = addr->ether_addr_octet[i];
-		const guint8 o = oui.ether_addr_octet[i];
-		const guint8 m = mask.ether_addr_octet[i];
-
-		addr->ether_addr_octet[i] = (a & ~m) | (o & m);
-	}
+    struct ether_addr  mask;
+    struct ether_addr  oui;
+    struct ether_addr *ouis;
+    gsize              ouis_len;
+    guint              i;
+
+    /* the second LSB of the first octet means
+     * "globally unique, OUI enforced, BIA (burned-in-address)"
+     * vs. "locally-administered". By default, set it to
+     * generate locally-administered addresses.
+     *
+     * Maybe be overwritten by a mask below. */
+    addr->ether_addr_octet[0] |= 2;
+
+    if (!generate_mac_address_mask || !*generate_mac_address_mask)
+        goto out;
+    if (!_nm_utils_generate_mac_address_mask_parse(generate_mac_address_mask,
+                                                   &mask,
+                                                   &ouis,
+                                                   &ouis_len,
+                                                   NULL))
+        goto out;
+
+    nm_assert((ouis == NULL) ^ (ouis_len != 0));
+    if (ouis) {
+        /* g_random_int() is good enough here. It uses a static GRand instance
+         * that is seeded from /dev/urandom. */
+        oui = ouis[g_random_int() % ouis_len];
+        g_free(ouis);
+    } else {
+        if (!nm_utils_hwaddr_aton(current_mac_address, &oui, ETH_ALEN))
+            goto out;
+    }
+
+    for (i = 0; i < ETH_ALEN; i++) {
+        const guint8 a = addr->ether_addr_octet[i];
+        const guint8 o = oui.ether_addr_octet[i];
+        const guint8 m = mask.ether_addr_octet[i];
+
+        addr->ether_addr_octet[i] = (a & ~m) | (o & m);
+    }
 
 out:
-	/* The LSB of the first octet must always be cleared,
-	 * it means Unicast vs. Multicast */
-	addr->ether_addr_octet[0] &= ~1;
+    /* The LSB of the first octet must always be cleared,
+     * it means Unicast vs. Multicast */
+    addr->ether_addr_octet[0] &= ~1;
 }
 
 char *
-nm_utils_hw_addr_gen_random_eth (const char *current_mac_address,
-                                 const char *generate_mac_address_mask)
+nm_utils_hw_addr_gen_random_eth(const char *current_mac_address,
+                                const char *generate_mac_address_mask)
 {
-	struct ether_addr bin_addr;
+    struct ether_addr bin_addr;
 
-	nm_utils_random_bytes (&bin_addr, ETH_ALEN);
-	_hw_addr_eth_complete (&bin_addr, current_mac_address, generate_mac_address_mask);
-	return nm_utils_hwaddr_ntoa (&bin_addr, ETH_ALEN);
+    nm_utils_random_bytes(&bin_addr, ETH_ALEN);
+    _hw_addr_eth_complete(&bin_addr, current_mac_address, generate_mac_address_mask);
+    return nm_utils_hwaddr_ntoa(&bin_addr, ETH_ALEN);
 }
 
 static char *
-_hw_addr_gen_stable_eth (NMUtilsStableType stable_type,
-                         const char *stable_id,
-                         const guint8 *host_id,
-                         gsize host_id_len,
-                         const char *ifname,
-                         const char *current_mac_address,
-                         const char *generate_mac_address_mask)
+_hw_addr_gen_stable_eth(NMUtilsStableType stable_type,
+                        const char *      stable_id,
+                        const guint8 *    host_id,
+                        gsize             host_id_len,
+                        const char *      ifname,
+                        const char *      current_mac_address,
+                        const char *      generate_mac_address_mask)
 {
-	nm_auto_free_checksum GChecksum *sum = NULL;
-	guint32 tmp;
-	guint8 digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
-	struct ether_addr bin_addr;
-	guint8 stable_type_uint8;
+    nm_auto_free_checksum GChecksum *sum = NULL;
+    guint32                          tmp;
+    guint8                           digest[NM_UTILS_CHECKSUM_LENGTH_SHA256];
+    struct ether_addr                bin_addr;
+    guint8                           stable_type_uint8;
 
-	nm_assert (stable_id);
-	nm_assert (host_id);
+    nm_assert(stable_id);
+    nm_assert(host_id);
 
-	sum = g_checksum_new (G_CHECKSUM_SHA256);
+    sum = g_checksum_new(G_CHECKSUM_SHA256);
 
-	host_id_len = MIN (host_id_len, G_MAXUINT32);
+    host_id_len = MIN(host_id_len, G_MAXUINT32);
 
-	nm_assert (stable_type < (NMUtilsStableType) 255);
-	stable_type_uint8 = stable_type;
-	g_checksum_update (sum, (const guchar *) &stable_type_uint8, sizeof (stable_type_uint8));
+    nm_assert(stable_type < (NMUtilsStableType) 255);
+    stable_type_uint8 = stable_type;
+    g_checksum_update(sum, (const guchar *) &stable_type_uint8, sizeof(stable_type_uint8));
 
-	tmp = htonl ((guint32) host_id_len);
-	g_checksum_update (sum, (const guchar *) &tmp, sizeof (tmp));
-	g_checksum_update (sum, (const guchar *) host_id, host_id_len);
-	g_checksum_update (sum, (const guchar *) (ifname ?: ""), ifname ? (strlen (ifname) + 1) : 1);
-	g_checksum_update (sum, (const guchar *) stable_id, strlen (stable_id) + 1);
+    tmp = htonl((guint32) host_id_len);
+    g_checksum_update(sum, (const guchar *) &tmp, sizeof(tmp));
+    g_checksum_update(sum, (const guchar *) host_id, host_id_len);
+    g_checksum_update(sum, (const guchar *) (ifname ?: ""), ifname ? (strlen(ifname) + 1) : 1);
+    g_checksum_update(sum, (const guchar *) stable_id, strlen(stable_id) + 1);
 
-	nm_utils_checksum_get_digest (sum, digest);
+    nm_utils_checksum_get_digest(sum, digest);
 
-	memcpy (&bin_addr, digest, ETH_ALEN);
-	_hw_addr_eth_complete (&bin_addr, current_mac_address, generate_mac_address_mask);
-	return nm_utils_hwaddr_ntoa (&bin_addr, ETH_ALEN);
+    memcpy(&bin_addr, digest, ETH_ALEN);
+    _hw_addr_eth_complete(&bin_addr, current_mac_address, generate_mac_address_mask);
+    return nm_utils_hwaddr_ntoa(&bin_addr, ETH_ALEN);
 }
 
 char *
-nm_utils_hw_addr_gen_stable_eth_impl (NMUtilsStableType stable_type,
-                                      const char *stable_id,
-                                      const guint8 *host_id,
-                                      gsize host_id_len,
-                                      const char *ifname,
-                                      const char *current_mac_address,
-                                      const char *generate_mac_address_mask)
+nm_utils_hw_addr_gen_stable_eth_impl(NMUtilsStableType stable_type,
+                                     const char *      stable_id,
+                                     const guint8 *    host_id,
+                                     gsize             host_id_len,
+                                     const char *      ifname,
+                                     const char *      current_mac_address,
+                                     const char *      generate_mac_address_mask)
 {
-	return _hw_addr_gen_stable_eth (stable_type, stable_id, host_id, host_id_len, ifname, current_mac_address, generate_mac_address_mask);
+    return _hw_addr_gen_stable_eth(stable_type,
+                                   stable_id,
+                                   host_id,
+                                   host_id_len,
+                                   ifname,
+                                   current_mac_address,
+                                   generate_mac_address_mask);
 }
 
 char *
-nm_utils_hw_addr_gen_stable_eth (NMUtilsStableType stable_type,
-                                 const char *stable_id,
-                                 const char *ifname,
-                                 const char *current_mac_address,
-                                 const char *generate_mac_address_mask)
+nm_utils_hw_addr_gen_stable_eth(NMUtilsStableType stable_type,
+                                const char *      stable_id,
+                                const char *      ifname,
+                                const char *      current_mac_address,
+                                const char *      generate_mac_address_mask)
 {
-	const guint8 *host_id;
-	gsize host_id_len;
+    const guint8 *host_id;
+    gsize         host_id_len;
 
-	g_return_val_if_fail (stable_id, NULL);
+    g_return_val_if_fail(stable_id, NULL);
 
-	nm_utils_host_id_get (&host_id, &host_id_len);
+    nm_utils_host_id_get(&host_id, &host_id_len);
 
-	return _hw_addr_gen_stable_eth (stable_type,
-	                                stable_id,
-	                                host_id,
-	                                host_id_len,
-	                                ifname,
-	                                current_mac_address,
-	                                generate_mac_address_mask);
+    return _hw_addr_gen_stable_eth(stable_type,
+                                   stable_id,
+                                   host_id,
+                                   host_id_len,
+                                   ifname,
+                                   current_mac_address,
+                                   generate_mac_address_mask);
 }
 
 /*****************************************************************************/
 
 GBytes *
-nm_utils_dhcp_client_id_mac (int arp_type,
-                             const guint8 *hwaddr,
-                             gsize hwaddr_len)
+nm_utils_dhcp_client_id_mac(int arp_type, const guint8 *hwaddr, gsize hwaddr_len)
 {
-	guint8 *client_id_buf;
-	const guint8 hwaddr_type = arp_type;
+    guint8 *     client_id_buf;
+    const guint8 hwaddr_type = arp_type;
 
-	if (!nm_utils_arp_type_get_hwaddr_relevant_part (arp_type, &hwaddr, &hwaddr_len))
-		g_return_val_if_reached (NULL);
+    if (!nm_utils_arp_type_get_hwaddr_relevant_part(arp_type, &hwaddr, &hwaddr_len))
+        g_return_val_if_reached(NULL);
 
-	client_id_buf = g_malloc (hwaddr_len + 1);
-	client_id_buf[0] = hwaddr_type;
-	memcpy (&client_id_buf[1], hwaddr, hwaddr_len);
-	return g_bytes_new_take (client_id_buf, hwaddr_len + 1);
+    client_id_buf    = g_malloc(hwaddr_len + 1);
+    client_id_buf[0] = hwaddr_type;
+    memcpy(&client_id_buf[1], hwaddr, hwaddr_len);
+    return g_bytes_new_take(client_id_buf, hwaddr_len + 1);
 }
 
-#define HASH_KEY ((const guint8[16]) { 0x80, 0x11, 0x8c, 0xc2, 0xfe, 0x4a, 0x03, 0xee, 0x3e, 0xd6, 0x0c, 0x6f, 0x36, 0x39, 0x14, 0x09 })
+#define HASH_KEY              \
+    ((const guint8[16]){0x80, \
+                        0x11, \
+                        0x8c, \
+                        0xc2, \
+                        0xfe, \
+                        0x4a, \
+                        0x03, \
+                        0xee, \
+                        0x3e, \
+                        0xd6, \
+                        0x0c, \
+                        0x6f, \
+                        0x36, \
+                        0x39, \
+                        0x14, \
+                        0x09})
 
 /**
  * nm_utils_create_dhcp_iaid:
@@ -3673,30 +4014,30 @@ nm_utils_dhcp_client_id_mac (int arp_type,
  *
  * Returns: the IAID in host byte order. */
 guint32
-nm_utils_create_dhcp_iaid (gboolean legacy_unstable_byteorder,
-                           const guint8 *interface_id,
-                           gsize interface_id_len)
+nm_utils_create_dhcp_iaid(gboolean      legacy_unstable_byteorder,
+                          const guint8 *interface_id,
+                          gsize         interface_id_len)
 {
-	guint64 u64;
-	guint32 u32;
-
-	u64 = c_siphash_hash (HASH_KEY, interface_id, interface_id_len);
-	u32 = (u64 & 0xffffffffu) ^ (u64 >> 32);
-	if (legacy_unstable_byteorder) {
-		/* legacy systemd code dhcp_identifier_set_iaid() generates the iaid
-		 * dependent on the host endianness. Since this function returns the IAID
-		 * in native-byte order, we need to account for that.
-		 *
-		 * On little endian systems, we want the legacy-behavior is identical to
-		 * the endianness-agnostic behavior. So, we need to swap the bytes on
-		 * big-endian systems.
-		 *
-		 * (https://github.com/systemd/systemd/pull/10614). */
-		return htole32 (u32);
-	} else {
-		/* we return the value as-is, in native byte order. */
-		return u32;
-	}
+    guint64 u64;
+    guint32 u32;
+
+    u64 = c_siphash_hash(HASH_KEY, interface_id, interface_id_len);
+    u32 = (u64 & 0xffffffffu) ^ (u64 >> 32);
+    if (legacy_unstable_byteorder) {
+        /* legacy systemd code dhcp_identifier_set_iaid() generates the iaid
+         * dependent on the host endianness. Since this function returns the IAID
+         * in native-byte order, we need to account for that.
+         *
+         * On little endian systems, we want the legacy-behavior is identical to
+         * the endianness-agnostic behavior. So, we need to swap the bytes on
+         * big-endian systems.
+         *
+         * (https://github.com/systemd/systemd/pull/10614). */
+        return htole32(u32);
+    } else {
+        /* we return the value as-is, in native byte order. */
+        return u32;
+    }
 }
 
 /**
@@ -3713,51 +4054,154 @@ nm_utils_create_dhcp_iaid (gboolean legacy_unstable_byteorder,
  * Returns: a %GBytes of generated client-id. This function cannot fail.
  */
 GBytes *
-nm_utils_dhcp_client_id_systemd_node_specific_full (guint32 iaid,
-                                                    const guint8 *machine_id,
-                                                    gsize machine_id_len)
+nm_utils_dhcp_client_id_systemd_node_specific_full(guint32       iaid,
+                                                   const guint8 *machine_id,
+                                                   gsize         machine_id_len)
+{
+    const guint16 DUID_TYPE_EN = 2;
+    const guint32 SYSTEMD_PEN  = 43793;
+    struct _nm_packed {
+        guint8  type;
+        guint32 iaid;
+        struct _nm_packed {
+            guint16 type;
+            union {
+                struct _nm_packed {
+                    /* DUID_TYPE_EN */
+                    guint32 pen;
+                    uint8_t id[8];
+                } en;
+            };
+        } duid;
+    } * client_id;
+    guint64 u64;
+
+    g_return_val_if_fail(machine_id, NULL);
+    g_return_val_if_fail(machine_id_len > 0, NULL);
+
+    client_id = g_malloc(sizeof(*client_id));
+
+    client_id->type = 255;
+    unaligned_write_be32(&client_id->iaid, iaid);
+    unaligned_write_be16(&client_id->duid.type, DUID_TYPE_EN);
+    unaligned_write_be32(&client_id->duid.en.pen, SYSTEMD_PEN);
+
+    u64 = htole64(c_siphash_hash(HASH_KEY, machine_id, machine_id_len));
+    memcpy(client_id->duid.en.id, &u64, sizeof(client_id->duid.en.id));
+
+    G_STATIC_ASSERT_EXPR(sizeof(*client_id) == 19);
+    return g_bytes_new_take(client_id, 19);
+}
+
+GBytes *
+nm_utils_dhcp_client_id_systemd_node_specific(guint32 iaid)
+{
+    return nm_utils_dhcp_client_id_systemd_node_specific_full(
+        iaid,
+        (const guint8 *) nm_utils_machine_id_bin(),
+        sizeof(NMUuid));
+}
+
+/*****************************************************************************/
+
+GBytes *
+nm_utils_generate_duid_llt(int arp_type, const guint8 *hwaddr, gsize hwaddr_len, gint64 time)
+{
+    guint8 *      arr;
+    const guint16 duid_type = htons(1);
+    const guint16 hw_type   = htons(arp_type);
+    const guint32 duid_time = htonl(NM_MAX(0, time - NM_UTILS_EPOCH_DATETIME_200001010000));
+
+    if (!nm_utils_arp_type_get_hwaddr_relevant_part(arp_type, &hwaddr, &hwaddr_len))
+        nm_assert_not_reached();
+
+    arr = g_new(guint8, (2u + 2u + 4u) + hwaddr_len);
+
+    memcpy(&arr[0], &duid_type, 2);
+    memcpy(&arr[2], &hw_type, 2);
+    memcpy(&arr[4], &duid_time, 4);
+    memcpy(&arr[8], hwaddr, hwaddr_len);
+
+    return g_bytes_new_take(arr, (2u + 2u + 4u) + hwaddr_len);
+}
+
+GBytes *
+nm_utils_generate_duid_ll(int arp_type, const guint8 *hwaddr, gsize hwaddr_len)
 {
-	const guint16 DUID_TYPE_EN = 2;
-	const guint32 SYSTEMD_PEN = 43793;
-	struct _nm_packed {
-		guint8 type;
-		guint32 iaid;
-		struct _nm_packed {
-			guint16 type;
-			union {
-				struct _nm_packed {
-						/* DUID_TYPE_EN */
-						guint32 pen;
-						uint8_t id[8];
-				} en;
-			};
-		} duid;
-	} *client_id;
-	guint64 u64;
-
-	g_return_val_if_fail (machine_id, NULL);
-	g_return_val_if_fail (machine_id_len > 0, NULL);
-
-	client_id = g_malloc (sizeof (*client_id));
-
-	client_id->type = 255;
-	unaligned_write_be32 (&client_id->iaid, iaid);
-	unaligned_write_be16 (&client_id->duid.type, DUID_TYPE_EN);
-	unaligned_write_be32 (&client_id->duid.en.pen, SYSTEMD_PEN);
-
-	u64 = htole64 (c_siphash_hash (HASH_KEY, machine_id, machine_id_len));
-	memcpy(client_id->duid.en.id, &u64, sizeof (client_id->duid.en.id));
-
-	G_STATIC_ASSERT_EXPR (sizeof (*client_id) == 19);
-	return g_bytes_new_take (client_id, 19);
+    guint8 *      arr;
+    const guint16 duid_type = htons(3);
+    const guint16 hw_type   = htons(arp_type);
+
+    if (!nm_utils_arp_type_get_hwaddr_relevant_part(arp_type, &hwaddr, &hwaddr_len))
+        nm_assert_not_reached();
+
+    arr = g_new(guint8, (2u + 2u) + hwaddr_len);
+
+    memcpy(&arr[0], &duid_type, 2);
+    memcpy(&arr[2], &hw_type, 2);
+    memcpy(&arr[4], hwaddr, hwaddr_len);
+
+    return g_bytes_new_take(arr, (2u + 2u) + hwaddr_len);
 }
 
 GBytes *
-nm_utils_dhcp_client_id_systemd_node_specific (guint32 iaid)
+nm_utils_generate_duid_uuid(const NMUuid *uuid)
 {
-	return nm_utils_dhcp_client_id_systemd_node_specific_full (iaid,
-	                                                           (const guint8 *) nm_utils_machine_id_bin (),
-	                                                           sizeof (NMUuid));
+    const guint16 duid_type = htons(4);
+    guint8 *      duid_buffer;
+
+    nm_assert(uuid);
+
+    /* Generate a DHCP Unique Identifier for DHCPv6 using the
+     * DUID-UUID method (see RFC 6355 section 4).  Format is:
+     *
+     * u16: type (DUID-UUID = 4)
+     * u8[16]: UUID bytes
+     */
+    G_STATIC_ASSERT_EXPR(sizeof(duid_type) == 2);
+    G_STATIC_ASSERT_EXPR(sizeof(*uuid) == 16);
+    duid_buffer = g_malloc(18);
+    memcpy(&duid_buffer[0], &duid_type, 2);
+    memcpy(&duid_buffer[2], uuid, 16);
+    return g_bytes_new_take(duid_buffer, 18);
+}
+
+GBytes *
+nm_utils_generate_duid_from_machine_id(void)
+{
+    static GBytes *volatile global_duid = NULL;
+    GBytes *p;
+
+again:
+    p = g_atomic_pointer_get(&global_duid);
+    if (G_UNLIKELY(!p)) {
+        nm_auto_free_checksum GChecksum *sum = NULL;
+        const NMUuid *                   machine_id;
+        union {
+            guint8 sha256[NM_UTILS_CHECKSUM_LENGTH_SHA256];
+            NMUuid uuid;
+        } digest;
+
+        machine_id = nm_utils_machine_id_bin();
+
+        /* Hash the machine ID so it's not leaked to the network.
+         *
+         * Optimally, we would choose an use case specific seed, but for historic
+         * reasons we didn't. */
+        sum = g_checksum_new(G_CHECKSUM_SHA256);
+        g_checksum_update(sum, (const guchar *) machine_id, sizeof(*machine_id));
+        nm_utils_checksum_get_digest(sum, digest.sha256);
+
+        G_STATIC_ASSERT_EXPR(sizeof(digest.sha256) > sizeof(digest.uuid));
+        p = nm_utils_generate_duid_uuid(&digest.uuid);
+
+        if (!g_atomic_pointer_compare_and_exchange(&global_duid, NULL, p)) {
+            g_bytes_unref(p);
+            goto again;
+        }
+    }
+
+    return g_bytes_ref(p);
 }
 
 /*****************************************************************************/
@@ -3772,12 +4216,12 @@ nm_utils_dhcp_client_id_systemd_node_specific (guint32 iaid)
  * is killed).
  */
 void
-nm_utils_setpgid (gpointer unused G_GNUC_UNUSED)
+nm_utils_setpgid(gpointer unused G_GNUC_UNUSED)
 {
-	pid_t pid;
+    pid_t pid;
 
-	pid = getpid ();
-	setpgid (pid, pid);
+    pid = getpid();
+    setpgid(pid, pid);
 }
 
 /**
@@ -3789,53 +4233,42 @@ nm_utils_setpgid (gpointer unused G_GNUC_UNUSED)
  * Converts @strings to a #GStrv and stores it in @value.
  */
 void
-nm_utils_g_value_set_strv (GValue *value, GPtrArray *strings)
+nm_utils_g_value_set_strv(GValue *value, GPtrArray *strings)
 {
-	char **strv;
-	guint i;
+    char **strv;
+    guint  i;
 
-	strv = g_new (char *, strings->len + 1);
-	for (i = 0; i < strings->len; i++) {
-		nm_assert (strings->pdata[i]);
-		strv[i] = g_strdup (strings->pdata[i]);
-	}
-	strv[i] = NULL;
+    strv = g_new(char *, strings->len + 1);
+    for (i = 0; i < strings->len; i++) {
+        nm_assert(strings->pdata[i]);
+        strv[i] = g_strdup(strings->pdata[i]);
+    }
+    strv[i] = NULL;
 
-	g_value_take_boxed (value, strv);
+    g_value_take_boxed(value, strv);
 }
 
 /*****************************************************************************/
 
 void
-nm_utils_ifname_cpy (char *dst, const char *name)
+nm_utils_ifname_cpy(char *dst, const char *name)
 {
-	int i;
+    int i;
 
-	g_return_if_fail (dst);
-	g_return_if_fail (name && name[0]);
+    g_return_if_fail(dst);
+    g_return_if_fail(name && name[0]);
 
-	nm_assert (nm_utils_ifname_valid_kernel (name, NULL));
+    nm_assert(nm_utils_ifname_valid_kernel(name, NULL));
 
-	/* ensures NUL padding of the entire IFNAMSIZ buffer. */
+    /* ensures NUL padding of the entire IFNAMSIZ buffer. */
 
-	for (i = 0; i < (int) IFNAMSIZ && name[i] != '\0'; i++)
-		dst[i] = name[i];
+    for (i = 0; i < (int) IFNAMSIZ && name[i] != '\0'; i++)
+        dst[i] = name[i];
 
-	nm_assert (name[i] == '\0');
+    nm_assert(name[i] == '\0');
 
-	for (; i < (int) IFNAMSIZ; i++)
-		dst[i] = '\0';
-}
-
-/*****************************************************************************/
-
-#define IPV4LL_NETWORK (htonl (0xA9FE0000L))
-#define IPV4LL_NETMASK (htonl (0xFFFF0000L))
-
-gboolean
-nm_utils_ip4_address_is_link_local (in_addr_t addr)
-{
-	return (addr & IPV4LL_NETMASK) == IPV4LL_NETWORK;
+    for (; i < (int) IFNAMSIZ; i++)
+        dst[i] = '\0';
 }
 
 /*****************************************************************************/
@@ -3845,113 +4278,111 @@ nm_utils_ip4_address_is_link_local (in_addr_t addr)
  * on the new timestamp @now.
  */
 guint32
-nm_utils_lifetime_rebase_relative_time_on_now (guint32 timestamp,
-                                               guint32 duration,
-                                               gint32 now)
+nm_utils_lifetime_rebase_relative_time_on_now(guint32 timestamp, guint32 duration, gint32 now)
 {
-	gint64 t;
-
-	nm_assert (now >= 0);
-
-	if (duration == NM_PLATFORM_LIFETIME_PERMANENT)
-		return NM_PLATFORM_LIFETIME_PERMANENT;
-
-	if (timestamp == 0) {
-		/* if the @timestamp is zero, assume it was just left unset and that the relative
-		 * @duration starts counting from @now. This is convenient to construct an address
-		 * and print it in nm_platform_ip4_address_to_string().
-		 *
-		 * In general it does not make sense to set the @duration without anchoring at
-		 * @timestamp because you don't know the absolute expiration time when looking
-		 * at the address at a later moment. */
-		timestamp = now;
-	}
-
-	/* For timestamp > now, just accept it and calculate the expected(?) result. */
-	t = (gint64) timestamp + (gint64) duration - (gint64) now;
-
-	if (t <= 0)
-		return 0;
-	if (t >= NM_PLATFORM_LIFETIME_PERMANENT)
-		return NM_PLATFORM_LIFETIME_PERMANENT - 1;
-	return t;
+    gint64 t;
+
+    nm_assert(now >= 0);
+
+    if (duration == NM_PLATFORM_LIFETIME_PERMANENT)
+        return NM_PLATFORM_LIFETIME_PERMANENT;
+
+    if (timestamp == 0) {
+        /* if the @timestamp is zero, assume it was just left unset and that the relative
+         * @duration starts counting from @now. This is convenient to construct an address
+         * and print it in nm_platform_ip4_address_to_string().
+         *
+         * In general it does not make sense to set the @duration without anchoring at
+         * @timestamp because you don't know the absolute expiration time when looking
+         * at the address at a later moment. */
+        timestamp = now;
+    }
+
+    /* For timestamp > now, just accept it and calculate the expected(?) result. */
+    t = (gint64) timestamp + (gint64) duration - (gint64) now;
+
+    if (t <= 0)
+        return 0;
+    if (t >= NM_PLATFORM_LIFETIME_PERMANENT)
+        return NM_PLATFORM_LIFETIME_PERMANENT - 1;
+    return t;
 }
 
 guint32
-nm_utils_lifetime_get (guint32 timestamp,
-                       guint32 lifetime,
-                       guint32 preferred,
-                       gint32 now,
-                       guint32 *out_preferred)
+nm_utils_lifetime_get(guint32  timestamp,
+                      guint32  lifetime,
+                      guint32  preferred,
+                      gint32   now,
+                      guint32 *out_preferred)
 {
-	guint32 t_lifetime, t_preferred;
-
-	nm_assert (now >= 0);
-
-	if (timestamp == 0 && lifetime == 0) {
-		/* We treat lifetime==0 && timestamp==0 addresses as permanent addresses to allow easy
-		 * creation of such addresses (without requiring to set the lifetime fields to
-		 * NM_PLATFORM_LIFETIME_PERMANENT). The real lifetime==0 addresses (E.g. DHCP6 telling us
-		 * to drop an address will have timestamp set.
-		 */
-		NM_SET_OUT (out_preferred, NM_PLATFORM_LIFETIME_PERMANENT);
-		g_return_val_if_fail (preferred == 0, NM_PLATFORM_LIFETIME_PERMANENT);
-		return NM_PLATFORM_LIFETIME_PERMANENT;
-	}
-
-	if (now <= 0)
-		now = nm_utils_get_monotonic_timestamp_sec ();
-
-	t_lifetime = nm_utils_lifetime_rebase_relative_time_on_now (timestamp, lifetime, now);
-	if (!t_lifetime) {
-		NM_SET_OUT (out_preferred, 0);
-		return 0;
-	}
-
-	t_preferred = nm_utils_lifetime_rebase_relative_time_on_now (timestamp, preferred, now);
-
-	NM_SET_OUT (out_preferred, MIN (t_preferred, t_lifetime));
-
-	/* Assert that non-permanent addresses have a (positive) @timestamp. nm_utils_lifetime_rebase_relative_time_on_now()
-	 * treats addresses with timestamp 0 as *now*. Addresses passed to _address_get_lifetime() always
-	 * should have a valid @timestamp, otherwise on every re-sync, their lifetime will be extended anew.
-	 */
-	g_return_val_if_fail (   timestamp != 0
-	                      || (   lifetime  == NM_PLATFORM_LIFETIME_PERMANENT
-	                          && preferred == NM_PLATFORM_LIFETIME_PERMANENT), t_lifetime);
-	g_return_val_if_fail (t_preferred <= t_lifetime, t_lifetime);
-
-	return t_lifetime;
+    guint32 t_lifetime, t_preferred;
+
+    nm_assert(now >= 0);
+
+    if (timestamp == 0 && lifetime == 0) {
+        /* We treat lifetime==0 && timestamp==0 addresses as permanent addresses to allow easy
+         * creation of such addresses (without requiring to set the lifetime fields to
+         * NM_PLATFORM_LIFETIME_PERMANENT). The real lifetime==0 addresses (E.g. DHCP6 telling us
+         * to drop an address will have timestamp set.
+         */
+        NM_SET_OUT(out_preferred, NM_PLATFORM_LIFETIME_PERMANENT);
+        g_return_val_if_fail(preferred == 0, NM_PLATFORM_LIFETIME_PERMANENT);
+        return NM_PLATFORM_LIFETIME_PERMANENT;
+    }
+
+    if (now <= 0)
+        now = nm_utils_get_monotonic_timestamp_sec();
+
+    t_lifetime = nm_utils_lifetime_rebase_relative_time_on_now(timestamp, lifetime, now);
+    if (!t_lifetime) {
+        NM_SET_OUT(out_preferred, 0);
+        return 0;
+    }
+
+    t_preferred = nm_utils_lifetime_rebase_relative_time_on_now(timestamp, preferred, now);
+
+    NM_SET_OUT(out_preferred, MIN(t_preferred, t_lifetime));
+
+    /* Assert that non-permanent addresses have a (positive) @timestamp. nm_utils_lifetime_rebase_relative_time_on_now()
+     * treats addresses with timestamp 0 as *now*. Addresses passed to _address_get_lifetime() always
+     * should have a valid @timestamp, otherwise on every re-sync, their lifetime will be extended anew.
+     */
+    g_return_val_if_fail(timestamp != 0
+                             || (lifetime == NM_PLATFORM_LIFETIME_PERMANENT
+                                 && preferred == NM_PLATFORM_LIFETIME_PERMANENT),
+                         t_lifetime);
+    g_return_val_if_fail(t_preferred <= t_lifetime, t_lifetime);
+
+    return t_lifetime;
 }
 
 const char *
-nm_utils_dnsmasq_status_to_string (int status, char *dest, gsize size)
+nm_utils_dnsmasq_status_to_string(int status, char *dest, gsize size)
 {
-	const char *msg;
-
-	nm_utils_to_string_buffer_init (&dest, &size);
-
-	if (status == 0)
-		msg = "Success";
-	else if (status == 1)
-		msg = "Configuration problem";
-	else if (status == 2)
-		msg = "Network access problem (address in use, permissions)";
-	else if (status == 3)
-		msg = "Filesystem problem (missing file/directory, permissions)";
-	else if (status == 4)
-		msg = "Memory allocation failure";
-	else if (status == 5)
-		msg = "Other problem";
-	else if (status >= 11) {
-		g_snprintf (dest, size, "Lease script failed with error %d", status - 10);
-		return dest;
-	}
-	else
-		msg = "Unknown problem";
-
-	g_snprintf (dest, size, "%s (%d)", msg, status);
-	return dest;
+    const char *msg;
+
+    nm_utils_to_string_buffer_init(&dest, &size);
+
+    if (status == 0)
+        msg = "Success";
+    else if (status == 1)
+        msg = "Configuration problem";
+    else if (status == 2)
+        msg = "Network access problem (address in use, permissions)";
+    else if (status == 3)
+        msg = "Filesystem problem (missing file/directory, permissions)";
+    else if (status == 4)
+        msg = "Memory allocation failure";
+    else if (status == 5)
+        msg = "Other problem";
+    else if (status >= 11) {
+        g_snprintf(dest, size, "Lease script failed with error %d", status - 10);
+        return dest;
+    } else
+        msg = "Unknown problem";
+
+    g_snprintf(dest, size, "%s (%d)", msg, status);
+    return dest;
 }
 
 /**
@@ -3964,42 +4395,42 @@ nm_utils_dnsmasq_status_to_string (int status, char *dest, gsize size)
  * append them to @domains.
  */
 void
-nm_utils_get_reverse_dns_domains_ip4 (guint32 addr, guint8 plen, GPtrArray *domains)
+nm_utils_get_reverse_dns_domains_ip4(guint32 addr, guint8 plen, GPtrArray *domains)
 {
-	guint32 ip, ip2, mask;
-	guchar *p;
-	guint octets;
-	guint i;
-	gsize len0, len;
-	char *str, *s;
-
-	g_return_if_fail (domains);
-	g_return_if_fail (plen <= 32);
-
-	if (!plen)
-		return;
-
-	octets = (plen - 1) / 8 + 1;
-	ip = ntohl (addr);
-	mask = 0xFFFFFFFF << (32 - plen);
-	ip &= mask;
-	ip2 = ip;
-
-	len0 = NM_STRLEN ("in-addr.arpa") + (4 * octets) + 1;
-	while ((ip2 & mask) == ip) {
-		addr = htonl (ip2);
-		p = (guchar *) &addr;
-
-		len = len0;
-		str = s = g_malloc (len);
-		for (i = octets; i > 0; i--)
-			nm_utils_strbuf_append (&s, &len, "%u.", p[i - 1] & 0xff);
-		nm_utils_strbuf_append_str (&s, &len, "in-addr.arpa");
-
-		g_ptr_array_add (domains, str);
-
-		ip2 += 1 << ((32 - plen) & ~7);
-	}
+    guint32 ip, ip2, mask;
+    guchar *p;
+    guint   octets;
+    guint   i;
+    gsize   len0, len;
+    char *  str, *s;
+
+    g_return_if_fail(domains);
+    g_return_if_fail(plen <= 32);
+
+    if (!plen)
+        return;
+
+    octets = (plen - 1) / 8 + 1;
+    ip     = ntohl(addr);
+    mask   = 0xFFFFFFFF << (32 - plen);
+    ip &= mask;
+    ip2 = ip;
+
+    len0 = NM_STRLEN("in-addr.arpa") + (4 * octets) + 1;
+    while ((ip2 & mask) == ip) {
+        addr = htonl(ip2);
+        p    = (guchar *) &addr;
+
+        len = len0;
+        str = s = g_malloc(len);
+        for (i = octets; i > 0; i--)
+            nm_utils_strbuf_append(&s, &len, "%u.", p[i - 1] & 0xff);
+        nm_utils_strbuf_append_str(&s, &len, "in-addr.arpa");
+
+        g_ptr_array_add(domains, str);
+
+        ip2 += 1 << ((32 - plen) & ~7);
+    }
 }
 
 /**
@@ -4012,613 +4443,679 @@ nm_utils_get_reverse_dns_domains_ip4 (guint32 addr, guint8 plen, GPtrArray *doma
  * append them to @domains.
  */
 void
-nm_utils_get_reverse_dns_domains_ip6 (const struct in6_addr *ip, guint8 plen, GPtrArray *domains)
+nm_utils_get_reverse_dns_domains_ip6(const struct in6_addr *ip, guint8 plen, GPtrArray *domains)
 {
-	struct in6_addr addr;
-	guint nibbles, bits, entries;
-	int i, j;
-	gsize len0, len;
-	char *str, *s;
+    struct in6_addr addr;
+    guint           nibbles, bits, entries;
+    int             i, j;
+    gsize           len0, len;
+    char *          str, *s;
 
-	g_return_if_fail (domains);
-	g_return_if_fail (plen <= 128);
+    g_return_if_fail(domains);
+    g_return_if_fail(plen <= 128);
 
-	if (!plen)
-		return;
+    if (!plen)
+        return;
 
-	memcpy (&addr, ip, sizeof (struct in6_addr));
-	nm_utils_ip6_address_clear_host_address (&addr, NULL, plen);
+    memcpy(&addr, ip, sizeof(struct in6_addr));
+    nm_utils_ip6_address_clear_host_address(&addr, NULL, plen);
 
-	/* Number of nibbles to include in domains */
-	nibbles = (plen - 1) / 4 + 1;
-	/* Prefix length in nibble */
-	bits = plen - ((plen - 1) / 4 * 4);
-	/* Number of domains */
-	entries = 1 << (4 - bits);
+    /* Number of nibbles to include in domains */
+    nibbles = (plen - 1) / 4 + 1;
+    /* Prefix length in nibble */
+    bits = plen - ((plen - 1) / 4 * 4);
+    /* Number of domains */
+    entries = 1 << (4 - bits);
 
-	len0 = NM_STRLEN ("ip6.arpa") + (2 * nibbles) + 1;
+    len0 = NM_STRLEN("ip6.arpa") + (2 * nibbles) + 1;
 
 #define N_SHIFT(x) ((x) % 2 ? 0 : 4)
 
-	for (i = 0; i < entries; i++) {
-		len = len0;
-		str = s = g_malloc (len);
+    for (i = 0; i < entries; i++) {
+        len = len0;
+        str = s = g_malloc(len);
 
-		for (j = nibbles - 1; j >= 0; j--)
-			nm_utils_strbuf_append (&s,
-			                        &len,
-			                        "%x.",
-			                        (addr.s6_addr[j / 2] >> N_SHIFT (j)) & 0xf);
-		nm_utils_strbuf_append_str (&s, &len, "ip6.arpa");
+        for (j = nibbles - 1; j >= 0; j--)
+            nm_utils_strbuf_append(&s, &len, "%x.", (addr.s6_addr[j / 2] >> N_SHIFT(j)) & 0xf);
+        nm_utils_strbuf_append_str(&s, &len, "ip6.arpa");
 
-		g_ptr_array_add (domains, str);
+        g_ptr_array_add(domains, str);
 
-		addr.s6_addr[(nibbles - 1) / 2] += 1 << N_SHIFT (nibbles - 1);
-	}
+        addr.s6_addr[(nibbles - 1) / 2] += 1 << N_SHIFT(nibbles - 1);
+    }
 
 #undef N_SHIFT
 }
 
 struct plugin_info {
-	char *path;
-	struct stat st;
+    char *      path;
+    struct stat st;
 };
 
 static int
-read_device_factory_paths_sort_fcn (gconstpointer a, gconstpointer b)
+read_device_factory_paths_sort_fcn(gconstpointer a, gconstpointer b)
 {
-	const struct plugin_info *da = a;
-	const struct plugin_info *db = b;
-	time_t ta, tb;
-
-	ta = MAX (da->st.st_mtime, da->st.st_ctime);
-	tb = MAX (db->st.st_mtime, db->st.st_ctime);
-
-	if (ta < tb)
-		return 1;
-	if (ta > tb)
-		return -1;
-	return 0;
+    const struct plugin_info *da = a;
+    const struct plugin_info *db = b;
+    time_t                    ta, tb;
+
+    ta = MAX(da->st.st_mtime, da->st.st_ctime);
+    tb = MAX(db->st.st_mtime, db->st.st_ctime);
+
+    if (ta < tb)
+        return 1;
+    if (ta > tb)
+        return -1;
+    return 0;
 }
 
 gboolean
-nm_utils_validate_plugin (const char *path, struct stat *st, GError **error)
+nm_utils_validate_plugin(const char *path, struct stat *st, GError **error)
 {
-	g_return_val_if_fail (path, FALSE);
-	g_return_val_if_fail (st, FALSE);
-	g_return_val_if_fail (!error || !*error, FALSE);
-
-	if (!S_ISREG (st->st_mode)) {
-		g_set_error_literal (error,
-		                     NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
-		                     "not a regular file");
-		return FALSE;
-	}
-
-	if (st->st_uid != 0) {
-		g_set_error_literal (error,
-		                     NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
-		                     "file has invalid owner (should be root)");
-		return FALSE;
-	}
-
-	if (st->st_mode & (S_IWGRP | S_IWOTH | S_ISUID)) {
-		g_set_error_literal (error,
-		                     NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN,
-		                     "file has invalid permissions");
-		return FALSE;
-	}
-
-	return TRUE;
+    g_return_val_if_fail(path, FALSE);
+    g_return_val_if_fail(st, FALSE);
+    g_return_val_if_fail(!error || !*error, FALSE);
+
+    if (!S_ISREG(st->st_mode)) {
+        g_set_error_literal(error, NM_UTILS_ERROR, NM_UTILS_ERROR_UNKNOWN, "not a regular file");
+        return FALSE;
+    }
+
+    if (st->st_uid != 0) {
+        g_set_error_literal(error,
+                            NM_UTILS_ERROR,
+                            NM_UTILS_ERROR_UNKNOWN,
+                            "file has invalid owner (should be root)");
+        return FALSE;
+    }
+
+    if (st->st_mode & (S_IWGRP | S_IWOTH | S_ISUID)) {
+        g_set_error_literal(error,
+                            NM_UTILS_ERROR,
+                            NM_UTILS_ERROR_UNKNOWN,
+                            "file has invalid permissions");
+        return FALSE;
+    }
+
+    return TRUE;
 }
 
 char **
-nm_utils_read_plugin_paths (const char *dirname, const char *prefix)
+nm_utils_read_plugin_paths(const char *dirname, const char *prefix)
 {
-	GDir *dir;
-	GError *error = NULL;
-	const char *item;
-	GArray *paths;
-	char **result;
-	guint i;
-
-	g_return_val_if_fail (dirname, NULL);
-	g_return_val_if_fail (prefix, NULL);
-
-	dir = g_dir_open (dirname, 0, &error);
-	if (!dir) {
-		nm_log_warn (LOGD_CORE, "device plugin: failed to open directory %s: %s",
-		             dirname,
-		             error->message);
-		g_clear_error (&error);
-		return NULL;
-	}
-
-	paths = g_array_new (FALSE, FALSE, sizeof (struct plugin_info));
-
-	while ((item = g_dir_read_name (dir))) {
-		int errsv;
-		struct plugin_info data;
-
-		if (!g_str_has_prefix (item, prefix))
-			continue;
-		if (!g_str_has_suffix (item, ".so"))
-			continue;
-
-		data.path = g_build_filename (dirname, item, NULL);
-
-		if (stat (data.path, &data.st) != 0) {
-			errsv = errno;
-			nm_log_warn (LOGD_CORE,
-			             "plugin: skip invalid file %s (error during stat: %s)",
-			             data.path, nm_strerror_native (errsv));
-			goto skip;
-		}
-
-		if (!nm_utils_validate_plugin (data.path, &data.st, &error)) {
-			nm_log_warn (LOGD_CORE,
-			             "plugin: skip invalid file %s: %s",
-			             data.path, error->message);
-			g_clear_error (&error);
-			goto skip;
-		}
-
-		g_array_append_val (paths, data);
-		continue;
+    GDir *      dir;
+    GError *    error = NULL;
+    const char *item;
+    GArray *    paths;
+    char **     result;
+    guint       i;
+
+    g_return_val_if_fail(dirname, NULL);
+    g_return_val_if_fail(prefix, NULL);
+
+    dir = g_dir_open(dirname, 0, &error);
+    if (!dir) {
+        nm_log_warn(LOGD_CORE,
+                    "device plugin: failed to open directory %s: %s",
+                    dirname,
+                    error->message);
+        g_clear_error(&error);
+        return NULL;
+    }
+
+    paths = g_array_new(FALSE, FALSE, sizeof(struct plugin_info));
+
+    while ((item = g_dir_read_name(dir))) {
+        int                errsv;
+        struct plugin_info data;
+
+        if (!g_str_has_prefix(item, prefix))
+            continue;
+        if (!g_str_has_suffix(item, ".so"))
+            continue;
+
+        data.path = g_build_filename(dirname, item, NULL);
+
+        if (stat(data.path, &data.st) != 0) {
+            errsv = errno;
+            nm_log_warn(LOGD_CORE,
+                        "plugin: skip invalid file %s (error during stat: %s)",
+                        data.path,
+                        nm_strerror_native(errsv));
+            goto skip;
+        }
+
+        if (!nm_utils_validate_plugin(data.path, &data.st, &error)) {
+            nm_log_warn(LOGD_CORE, "plugin: skip invalid file %s: %s", data.path, error->message);
+            g_clear_error(&error);
+            goto skip;
+        }
+
+        g_array_append_val(paths, data);
+        continue;
 skip:
-		g_free (data.path);
-	}
-	g_dir_close (dir);
+        g_free(data.path);
+    }
+    g_dir_close(dir);
 
-	/* sort filenames by modification time. */
-	g_array_sort (paths, read_device_factory_paths_sort_fcn);
+    /* sort filenames by modification time. */
+    g_array_sort(paths, read_device_factory_paths_sort_fcn);
 
-	result = g_new (char *, paths->len + 1);
-	for (i = 0; i < paths->len; i++)
-		result[i] = g_array_index (paths, struct plugin_info, i).path;
-	result[i] = NULL;
+    result = g_new(char *, paths->len + 1);
+    for (i = 0; i < paths->len; i++)
+        result[i] = g_array_index(paths, struct plugin_info, i).path;
+    result[i] = NULL;
 
-	g_array_free (paths, TRUE);
-	return result;
+    g_array_free(paths, TRUE);
+    return result;
 }
 
 char *
-nm_utils_format_con_diff_for_audit (GHashTable *diff)
+nm_utils_format_con_diff_for_audit(GHashTable *diff)
 {
-	GHashTable *setting_diff;
-	char *setting_name, *prop_name;
-	GHashTableIter iter, iter2;
-	GString *str;
+    GHashTable *   setting_diff;
+    char *         setting_name, *prop_name;
+    GHashTableIter iter, iter2;
+    GString *      str;
 
-	str = g_string_sized_new (32);
-	g_hash_table_iter_init (&iter, diff);
+    str = g_string_sized_new(32);
+    g_hash_table_iter_init(&iter, diff);
 
-	while (g_hash_table_iter_next (&iter,
-	                               (gpointer *) &setting_name,
-	                               (gpointer *) &setting_diff)) {
-		if (!setting_diff)
-			continue;
+    while (g_hash_table_iter_next(&iter, (gpointer *) &setting_name, (gpointer *) &setting_diff)) {
+        if (!setting_diff)
+            continue;
 
-		g_hash_table_iter_init (&iter2, setting_diff);
+        g_hash_table_iter_init(&iter2, setting_diff);
 
-		while (g_hash_table_iter_next (&iter2, (gpointer *) &prop_name, NULL))
-			g_string_append_printf (str, "%s.%s,", setting_name, prop_name);
-	}
+        while (g_hash_table_iter_next(&iter2, (gpointer *) &prop_name, NULL))
+            g_string_append_printf(str, "%s.%s,", setting_name, prop_name);
+    }
 
-	if (str->len)
-		str->str[str->len - 1] = '\0';
+    if (str->len)
+        str->str[str->len - 1] = '\0';
 
-	return g_string_free (str, FALSE);
+    return g_string_free(str, FALSE);
 }
 
 const char *
-nm_utils_parse_dns_domain (const char *domain, gboolean *is_routing)
+nm_utils_parse_dns_domain(const char *domain, gboolean *is_routing)
 {
-	g_return_val_if_fail (domain, NULL);
-	g_return_val_if_fail (domain[0], NULL);
-
-	if (domain[0] == '~') {
-		domain++;
-		NM_SET_OUT (is_routing, TRUE);
-	} else
-		NM_SET_OUT (is_routing, FALSE);
+    g_return_val_if_fail(domain, NULL);
+    g_return_val_if_fail(domain[0], NULL);
 
-	return domain;
-}
-
-/*****************************************************************************/
+    if (domain[0] == '~') {
+        domain++;
+        NM_SET_OUT(is_routing, TRUE);
+    } else
+        NM_SET_OUT(is_routing, FALSE);
 
-GVariant *
-nm_utils_strdict_to_variant (GHashTable *options)
-{
-	GVariantBuilder builder;
-	gs_free NMUtilsNamedValue *values = NULL;
-	guint i;
-	guint n;
-
-	values = nm_utils_named_values_from_str_dict (options, &n);
-
-	g_variant_builder_init (&builder, G_VARIANT_TYPE ("a{sv}"));
-	for (i = 0; i < n; i++) {
-		g_variant_builder_add (&builder,
-		                       "{sv}",
-		                       values[i].name,
-		                       g_variant_new_string (values[i].value_str));
-	}
-	return g_variant_builder_end (&builder);
+    return domain;
 }
 
 /*****************************************************************************/
 
 static guint32
-get_max_rate_ht_20 (int mcs)
+get_max_rate_ht_20(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 6500000;
-	case 1:
-	case 8:  return 13000000;
-	case 2:
-	case 16: return 19500000;
-	case 3:
-	case 9:
-	case 24: return 26000000;
-	case 4:
-	case 10:
-	case 17: return 39000000;
-	case 5:
-	case 11:
-	case 25: return 52000000;
-	case 6:
-	case 18: return 58500000;
-	case 7:  return 65000000;
-	case 12:
-	case 19:
-	case 26: return 78000000;
-	case 13:
-	case 27: return 104000000;
-	case 14:
-	case 20: return 117000000;
-	case 15: return 130000000;
-	case 21:
-	case 28: return 156000000;
-	case 22: return 175500000;
-	case 23: return 195000000;
-	case 29: return 208000000;
-	case 30: return 234000000;
-	case 31: return 260000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 6500000;
+    case 1:
+    case 8:
+        return 13000000;
+    case 2:
+    case 16:
+        return 19500000;
+    case 3:
+    case 9:
+    case 24:
+        return 26000000;
+    case 4:
+    case 10:
+    case 17:
+        return 39000000;
+    case 5:
+    case 11:
+    case 25:
+        return 52000000;
+    case 6:
+    case 18:
+        return 58500000;
+    case 7:
+        return 65000000;
+    case 12:
+    case 19:
+    case 26:
+        return 78000000;
+    case 13:
+    case 27:
+        return 104000000;
+    case 14:
+    case 20:
+        return 117000000;
+    case 15:
+        return 130000000;
+    case 21:
+    case 28:
+        return 156000000;
+    case 22:
+        return 175500000;
+    case 23:
+        return 195000000;
+    case 29:
+        return 208000000;
+    case 30:
+        return 234000000;
+    case 31:
+        return 260000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_ht_40 (int mcs)
+get_max_rate_ht_40(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 13500000;
-	case 1:
-	case 8:  return 27000000;
-	case 2:  return 40500000;
-	case 3:
-	case 9:
-	case 24: return 54000000;
-	case 4:
-	case 10:
-	case 17: return 81000000;
-	case 5:
-	case 11:
-	case 25: return 108000000;
-	case 6:
-	case 18: return 121500000;
-	case 7:  return 135000000;
-	case 12:
-	case 19:
-	case 26: return 162000000;
-	case 13:
-	case 27: return 216000000;
-	case 14:
-	case 20: return 243000000;
-	case 15: return 270000000;
-	case 16: return 40500000;
-	case 21:
-	case 28: return 324000000;
-	case 22: return 364500000;
-	case 23: return 405000000;
-	case 29: return 432000000;
-	case 30: return 486000000;
-	case 31: return 540000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 13500000;
+    case 1:
+    case 8:
+        return 27000000;
+    case 2:
+        return 40500000;
+    case 3:
+    case 9:
+    case 24:
+        return 54000000;
+    case 4:
+    case 10:
+    case 17:
+        return 81000000;
+    case 5:
+    case 11:
+    case 25:
+        return 108000000;
+    case 6:
+    case 18:
+        return 121500000;
+    case 7:
+        return 135000000;
+    case 12:
+    case 19:
+    case 26:
+        return 162000000;
+    case 13:
+    case 27:
+        return 216000000;
+    case 14:
+    case 20:
+        return 243000000;
+    case 15:
+        return 270000000;
+    case 16:
+        return 40500000;
+    case 21:
+    case 28:
+        return 324000000;
+    case 22:
+        return 364500000;
+    case 23:
+        return 405000000;
+    case 29:
+        return 432000000;
+    case 30:
+        return 486000000;
+    case 31:
+        return 540000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_80_ss1 (int mcs)
+get_max_rate_vht_80_ss1(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 29300000;
-	case 1:  return 58500000;
-	case 2:  return 87800000;
-	case 3:  return 117000000;
-	case 4:  return 175500000;
-	case 5:  return 234000000;
-	case 6:  return 263300000;
-	case 7:  return 292500000;
-	case 8:  return 351000000;
-	case 9:  return 390000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 29300000;
+    case 1:
+        return 58500000;
+    case 2:
+        return 87800000;
+    case 3:
+        return 117000000;
+    case 4:
+        return 175500000;
+    case 5:
+        return 234000000;
+    case 6:
+        return 263300000;
+    case 7:
+        return 292500000;
+    case 8:
+        return 351000000;
+    case 9:
+        return 390000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_80_ss2 (int mcs)
+get_max_rate_vht_80_ss2(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 58500000;
-	case 1:  return 117000000;
-	case 2:  return 175500000;
-	case 3:  return 234000000;
-	case 4:  return 351000000;
-	case 5:  return 468000000;
-	case 6:  return 526500000;
-	case 7:  return 585000000;
-	case 8:  return 702000000;
-	case 9:  return 780000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 58500000;
+    case 1:
+        return 117000000;
+    case 2:
+        return 175500000;
+    case 3:
+        return 234000000;
+    case 4:
+        return 351000000;
+    case 5:
+        return 468000000;
+    case 6:
+        return 526500000;
+    case 7:
+        return 585000000;
+    case 8:
+        return 702000000;
+    case 9:
+        return 780000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_80_ss3 (int mcs)
+get_max_rate_vht_80_ss3(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 87800000;
-	case 1:  return 175500000;
-	case 2:  return 263300000;
-	case 3:  return 351000000;
-	case 4:  return 526500000;
-	case 5:  return 702000000;
-	case 6:  return 0;
-	case 7:  return 877500000;
-	case 8:  return 105300000;
-	case 9:  return 117000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 87800000;
+    case 1:
+        return 175500000;
+    case 2:
+        return 263300000;
+    case 3:
+        return 351000000;
+    case 4:
+        return 526500000;
+    case 5:
+        return 702000000;
+    case 6:
+        return 0;
+    case 7:
+        return 877500000;
+    case 8:
+        return 105300000;
+    case 9:
+        return 117000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_160_ss1 (int mcs)
+get_max_rate_vht_160_ss1(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 58500000;
-	case 1:  return 117000000;
-	case 2:  return 175500000;
-	case 3:  return 234000000;
-	case 4:  return 351000000;
-	case 5:  return 468000000;
-	case 6:  return 526500000;
-	case 7:  return 585000000;
-	case 8:  return 702000000;
-	case 9:  return 780000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 58500000;
+    case 1:
+        return 117000000;
+    case 2:
+        return 175500000;
+    case 3:
+        return 234000000;
+    case 4:
+        return 351000000;
+    case 5:
+        return 468000000;
+    case 6:
+        return 526500000;
+    case 7:
+        return 585000000;
+    case 8:
+        return 702000000;
+    case 9:
+        return 780000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_160_ss2 (int mcs)
+get_max_rate_vht_160_ss2(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 117000000;
-	case 1:  return 234000000;
-	case 2:  return 351000000;
-	case 3:  return 468000000;
-	case 4:  return 702000000;
-	case 5:  return 936000000;
-	case 6:  return 1053000000;
-	case 7:  return 1170000000;
-	case 8:  return 1404000000;
-	case 9:  return 1560000000;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 117000000;
+    case 1:
+        return 234000000;
+    case 2:
+        return 351000000;
+    case 3:
+        return 468000000;
+    case 4:
+        return 702000000;
+    case 5:
+        return 936000000;
+    case 6:
+        return 1053000000;
+    case 7:
+        return 1170000000;
+    case 8:
+        return 1404000000;
+    case 9:
+        return 1560000000;
+    }
+    return 0;
 }
 
 static guint32
-get_max_rate_vht_160_ss3 (int mcs)
+get_max_rate_vht_160_ss3(int mcs)
 {
-	switch (mcs) {
-	case 0:  return 175500000;
-	case 1:  return 351000000;
-	case 2:  return 526500000;
-	case 3:  return 702000000;
-	case 4:  return 1053000000;
-	case 5:  return 1404000000;
-	case 6:  return 1579500000;
-	case 7:  return 1755000000;
-	case 8:  return 2106000000;
-	case 9:  return 0;
-	}
-	return 0;
+    switch (mcs) {
+    case 0:
+        return 175500000;
+    case 1:
+        return 351000000;
+    case 2:
+        return 526500000;
+    case 3:
+        return 702000000;
+    case 4:
+        return 1053000000;
+    case 5:
+        return 1404000000;
+    case 6:
+        return 1579500000;
+    case 7:
+        return 1755000000;
+    case 8:
+        return 2106000000;
+    case 9:
+        return 0;
+    }
+    return 0;
 }
 
 static gboolean
-get_max_rate_ht (const guint8 *bytes, guint len, guint32 *out_maxrate)
+get_max_rate_ht(const guint8 *bytes, guint len, guint32 *out_maxrate)
 {
-	guint32 i;
-	guint8 ht_cap_info;
-	const guint8 *supported_mcs_set;
-	guint32 rate;
-
-	/* http://standards.ieee.org/getieee802/download/802.11-2012.pdf
-	 * https://mrncciew.com/2014/10/19/cwap-ht-capabilities-ie/
-	 */
-
-	if (len != 26)
-		return FALSE;
-
-	ht_cap_info = bytes[0];
-	supported_mcs_set = &bytes[3];
-	*out_maxrate = 0;
-
-	/* Find the maximum supported mcs rate */
-	for (i = 0; i <= 76; i++) {
-		const unsigned mcs_octet = i / 8;
-		const unsigned MCS_RATE_BIT = 1 << i % 8;
-
-		if (supported_mcs_set[mcs_octet] & MCS_RATE_BIT) {
-			/* Check for 40Mhz wide channel support */
-			if (ht_cap_info & (1 << 1))
-				rate = get_max_rate_ht_40 (i);
-			else
-				rate = get_max_rate_ht_20 (i);
-
-			if (rate > *out_maxrate)
-				*out_maxrate = rate;
-		}
-	}
-
-	return TRUE;
+    guint32       i;
+    guint8        ht_cap_info;
+    const guint8 *supported_mcs_set;
+    guint32       rate;
+
+    /* http://standards.ieee.org/getieee802/download/802.11-2012.pdf
+     * https://mrncciew.com/2014/10/19/cwap-ht-capabilities-ie/
+     */
+
+    if (len != 26)
+        return FALSE;
+
+    ht_cap_info       = bytes[0];
+    supported_mcs_set = &bytes[3];
+    *out_maxrate      = 0;
+
+    /* Find the maximum supported mcs rate */
+    for (i = 0; i <= 76; i++) {
+        const unsigned mcs_octet    = i / 8;
+        const unsigned MCS_RATE_BIT = 1 << i % 8;
+
+        if (supported_mcs_set[mcs_octet] & MCS_RATE_BIT) {
+            /* Check for 40Mhz wide channel support */
+            if (ht_cap_info & (1 << 1))
+                rate = get_max_rate_ht_40(i);
+            else
+                rate = get_max_rate_ht_20(i);
+
+            if (rate > *out_maxrate)
+                *out_maxrate = rate;
+        }
+    }
+
+    return TRUE;
 }
 
 static gboolean
-get_max_rate_vht (const guint8 *bytes, guint len, guint32 *out_maxrate)
+get_max_rate_vht(const guint8 *bytes, guint len, guint32 *out_maxrate)
 {
-	guint32 mcs, m;
-	guint8 vht_cap, tx_map;
-
-	/* https://tda802dot11.blogspot.it/2014/10/vht-capabilities-element-vht.html
-	 * http://chimera.labs.oreilly.com/books/1234000001739/ch03.html#management_frames */
-
-	if (len != 12)
-		return FALSE;
-
-	vht_cap = bytes[0];
-	tx_map = bytes[8];
-
-	/* Check for mcs rates 8 and 9 support */
-	if (tx_map & 0x2a)
-		mcs = 9;
-	else if (tx_map & 0x15)
-		mcs = 8;
-	else
-		mcs = 7;
-
-	/* Check for 160Mhz wide channel support and
-	 * spatial stream support */
-	if (vht_cap & (1 << 2)) {
-		if (tx_map & 0x30)
-			m = get_max_rate_vht_160_ss3 (mcs);
-		else if (tx_map & 0x0C)
-			m = get_max_rate_vht_160_ss2 (mcs);
-		else
-			m = get_max_rate_vht_160_ss1 (mcs);
-	} else {
-		if (tx_map & 0x30)
-			m = get_max_rate_vht_80_ss3 (mcs);
-		else if (tx_map & 0x0C)
-			m = get_max_rate_vht_80_ss2 (mcs);
-		else
-			m = get_max_rate_vht_80_ss1 (mcs);
-	}
-
-	*out_maxrate = m;
-	return TRUE;
+    guint32 mcs, m;
+    guint8  vht_cap, tx_map;
+
+    /* https://tda802dot11.blogspot.it/2014/10/vht-capabilities-element-vht.html
+     * http://chimera.labs.oreilly.com/books/1234000001739/ch03.html#management_frames */
+
+    if (len != 12)
+        return FALSE;
+
+    vht_cap = bytes[0];
+    tx_map  = bytes[8];
+
+    /* Check for mcs rates 8 and 9 support */
+    if (tx_map & 0x2a)
+        mcs = 9;
+    else if (tx_map & 0x15)
+        mcs = 8;
+    else
+        mcs = 7;
+
+    /* Check for 160Mhz wide channel support and
+     * spatial stream support */
+    if (vht_cap & (1 << 2)) {
+        if (tx_map & 0x30)
+            m = get_max_rate_vht_160_ss3(mcs);
+        else if (tx_map & 0x0C)
+            m = get_max_rate_vht_160_ss2(mcs);
+        else
+            m = get_max_rate_vht_160_ss1(mcs);
+    } else {
+        if (tx_map & 0x30)
+            m = get_max_rate_vht_80_ss3(mcs);
+        else if (tx_map & 0x0C)
+            m = get_max_rate_vht_80_ss2(mcs);
+        else
+            m = get_max_rate_vht_80_ss1(mcs);
+    }
+
+    *out_maxrate = m;
+    return TRUE;
 }
 
 /* Management Frame Information Element IDs, ieee80211_eid */
-#define WLAN_EID_HT_CAPABILITY       45
-#define WLAN_EID_VHT_CAPABILITY     191
-#define WLAN_EID_VENDOR_SPECIFIC    221
+#define WLAN_EID_HT_CAPABILITY   45
+#define WLAN_EID_VHT_CAPABILITY  191
+#define WLAN_EID_VENDOR_SPECIFIC 221
 
 void
-nm_wifi_utils_parse_ies (const guint8 *bytes,
-                         gsize len,
-                         guint32 *out_max_rate,
-                         gboolean *out_metered,
-                         gboolean *out_owe_transition_mode)
+nm_wifi_utils_parse_ies(const guint8 *bytes,
+                        gsize         len,
+                        guint32 *     out_max_rate,
+                        gboolean *    out_metered,
+                        gboolean *    out_owe_transition_mode)
 {
-	guint8 id, elem_len;
-	guint32 m;
-
-	NM_SET_OUT (out_max_rate, 0);
-	NM_SET_OUT (out_metered, FALSE);
-	NM_SET_OUT (out_owe_transition_mode, FALSE);
-
-	while (len) {
-		if (len < 2)
-			break;
-
-		id = *bytes++;
-		elem_len = *bytes++;
-		len -= 2;
-
-		if (elem_len > len)
-			break;
-
-		switch (id) {
-		case WLAN_EID_HT_CAPABILITY:
-			if (out_max_rate) {
-				if (get_max_rate_ht (bytes, elem_len, &m))
-					*out_max_rate = NM_MAX (*out_max_rate, m);
-			}
-			break;
-		case WLAN_EID_VHT_CAPABILITY:
-			if (out_max_rate) {
-				if (get_max_rate_vht (bytes, elem_len, &m))
-					*out_max_rate = NM_MAX (*out_max_rate, m);
-			}
-			break;
-		case WLAN_EID_VENDOR_SPECIFIC:
-			if (   len == 8
-			    && bytes[0] == 0x00            /* OUI: Microsoft */
-			    && bytes[1] == 0x50
-			    && bytes[2] == 0xf2
-			    && bytes[3] == 0x11)           /* OUI type: Network cost */
-				NM_SET_OUT (out_metered, (bytes[7] > 1)); /* Cost level > 1 */
-			if (   elem_len >= 10
-			    && bytes[0] == 0x50            /* OUI: WiFi Alliance */
-			    && bytes[1] == 0x6f
-			    && bytes[2] == 0x9a
-			    && bytes[3] == 0x1c)           /* OUI type: OWE Transition Mode */
-				NM_SET_OUT (out_owe_transition_mode, TRUE);
-			break;
-		}
-
-		len -= elem_len;
-		bytes += elem_len;
-	}
+    guint8  id, elem_len;
+    guint32 m;
+
+    NM_SET_OUT(out_max_rate, 0);
+    NM_SET_OUT(out_metered, FALSE);
+    NM_SET_OUT(out_owe_transition_mode, FALSE);
+
+    while (len) {
+        if (len < 2)
+            break;
+
+        id       = *bytes++;
+        elem_len = *bytes++;
+        len -= 2;
+
+        if (elem_len > len)
+            break;
+
+        switch (id) {
+        case WLAN_EID_HT_CAPABILITY:
+            if (out_max_rate) {
+                if (get_max_rate_ht(bytes, elem_len, &m))
+                    *out_max_rate = NM_MAX(*out_max_rate, m);
+            }
+            break;
+        case WLAN_EID_VHT_CAPABILITY:
+            if (out_max_rate) {
+                if (get_max_rate_vht(bytes, elem_len, &m))
+                    *out_max_rate = NM_MAX(*out_max_rate, m);
+            }
+            break;
+        case WLAN_EID_VENDOR_SPECIFIC:
+            if (len == 8 && bytes[0] == 0x00 /* OUI: Microsoft */
+                && bytes[1] == 0x50 && bytes[2] == 0xf2
+                && bytes[3] == 0x11)                     /* OUI type: Network cost */
+                NM_SET_OUT(out_metered, (bytes[7] > 1)); /* Cost level > 1 */
+            if (elem_len >= 10 && bytes[0] == 0x50       /* OUI: WiFi Alliance */
+                && bytes[1] == 0x6f && bytes[2] == 0x9a
+                && bytes[3] == 0x1c) /* OUI type: OWE Transition Mode */
+                NM_SET_OUT(out_owe_transition_mode, TRUE);
+            break;
+        }
+
+        len -= elem_len;
+        bytes += elem_len;
+    }
 }
 
 /*****************************************************************************/
 
 guint8
-nm_wifi_utils_level_to_quality (int val)
+nm_wifi_utils_level_to_quality(int val)
 {
-	if (val < 0) {
-		/* Assume dBm already; rough conversion: best = -40, worst = -100 */
-		val = abs (CLAMP (val, -100, -40) + 40);  /* normalize to 0 */
-		val = 100 - (int) ((100.0 * (double) val) / 60.0);
-	} else if (val > 110 && val < 256) {
-		/* assume old-style WEXT 8-bit unsigned signal level */
-		val -= 256;  /* subtract 256 to convert to dBm */
-		val = abs (CLAMP (val, -100, -40) + 40);  /* normalize to 0 */
-		val = 100 - (int) ((100.0 * (double) val) / 60.0);
-	} else {
-		/* Assume signal is a "quality" percentage */
-	}
-
-	return CLAMP (val, 0, 100);
+    if (val < 0) {
+        /* Assume dBm already; rough conversion: best = -40, worst = -100 */
+        val = abs(CLAMP(val, -100, -40) + 40); /* normalize to 0 */
+        val = 100 - (int) ((100.0 * (double) val) / 60.0);
+    } else if (val > 110 && val < 256) {
+        /* assume old-style WEXT 8-bit unsigned signal level */
+        val -= 256;                            /* subtract 256 to convert to dBm */
+        val = abs(CLAMP(val, -100, -40) + 40); /* normalize to 0 */
+        val = 100 - (int) ((100.0 * (double) val) / 60.0);
+    } else {
+        /* Assume signal is a "quality" percentage */
+    }
+
+    return CLAMP(val, 0, 100);
 }
 
 /*****************************************************************************/
 
-NM_UTILS_ENUM2STR_DEFINE (nm_icmpv6_router_pref_to_string, NMIcmpv6RouterPref,
-	NM_UTILS_ENUM2STR (NM_ICMPV6_ROUTER_PREF_LOW,     "low"),
-	NM_UTILS_ENUM2STR (NM_ICMPV6_ROUTER_PREF_MEDIUM,  "medium"),
-	NM_UTILS_ENUM2STR (NM_ICMPV6_ROUTER_PREF_HIGH,    "high"),
-	NM_UTILS_ENUM2STR (NM_ICMPV6_ROUTER_PREF_INVALID, "invalid"),
-);
-
-NM_UTILS_LOOKUP_STR_DEFINE (nm_activation_type_to_string, NMActivationType,
-	NM_UTILS_LOOKUP_DEFAULT_WARN ("(unknown)"),
-	NM_UTILS_LOOKUP_STR_ITEM (NM_ACTIVATION_TYPE_MANAGED,  "managed"),
-	NM_UTILS_LOOKUP_STR_ITEM (NM_ACTIVATION_TYPE_ASSUME,   "assume"),
-	NM_UTILS_LOOKUP_STR_ITEM (NM_ACTIVATION_TYPE_EXTERNAL, "external"),
-)
+NM_UTILS_ENUM2STR_DEFINE(nm_icmpv6_router_pref_to_string,
+                         NMIcmpv6RouterPref,
+                         NM_UTILS_ENUM2STR(NM_ICMPV6_ROUTER_PREF_LOW, "low"),
+                         NM_UTILS_ENUM2STR(NM_ICMPV6_ROUTER_PREF_MEDIUM, "medium"),
+                         NM_UTILS_ENUM2STR(NM_ICMPV6_ROUTER_PREF_HIGH, "high"),
+                         NM_UTILS_ENUM2STR(NM_ICMPV6_ROUTER_PREF_INVALID, "invalid"), );
+
+NM_UTILS_LOOKUP_STR_DEFINE(nm_activation_type_to_string,
+                           NMActivationType,
+                           NM_UTILS_LOOKUP_DEFAULT_WARN("(unknown)"),
+                           NM_UTILS_LOOKUP_STR_ITEM(NM_ACTIVATION_TYPE_MANAGED, "managed"),
+                           NM_UTILS_LOOKUP_STR_ITEM(NM_ACTIVATION_TYPE_ASSUME, "assume"),
+                           NM_UTILS_LOOKUP_STR_ITEM(NM_ACTIVATION_TYPE_EXTERNAL, "external"), );