|
|
ab7d06 |
From 0551c1cb8106bf3483433fd9da6e391b9c2c2712 Mon Sep 17 00:00:00 2001
|
|
|
ab7d06 |
From: Thomas Haller <thaller@redhat.com>
|
|
|
ab7d06 |
Date: Thu, 8 Oct 2015 11:11:42 +0200
|
|
|
ab7d06 |
Subject: [PATCH 1/1] device: fix race wrongly managing external-down device
|
|
|
ab7d06 |
due to late udev signal
|
|
|
ab7d06 |
|
|
|
ab7d06 |
Executing:
|
|
|
ab7d06 |
|
|
|
ab7d06 |
# brctl addbr lbr0
|
|
|
ab7d06 |
# ip addr add 10.1.1.1/24 dev lbr0
|
|
|
ab7d06 |
# ip link set lbr0 up
|
|
|
ab7d06 |
|
|
|
ab7d06 |
can result in a race so that NetworkManager would manage the device
|
|
|
ab7d06 |
(and clear the IP addresses).
|
|
|
ab7d06 |
|
|
|
ab7d06 |
It happens, when NetworkManager first receives platform signals that
|
|
|
ab7d06 |
the device is already up:
|
|
|
ab7d06 |
|
|
|
ab7d06 |
signal: link changed: 11: lbr0 <UP,LOWER_UP;broadcast,multicast,up,running,lowerup> mtu 1500 arp 1 bridge* not-init addrgenmode eui64 addr D2:A1:B4:17:18:F2 driver bridge
|
|
|
ab7d06 |
|
|
|
ab7d06 |
Note that the device is still unknown via udev (not-init). The
|
|
|
ab7d06 |
unmanaged-state NM_UNMANAGED_EXTERNAL_DOWN gets cleared, but the
|
|
|
ab7d06 |
device still stays unmanaged.
|
|
|
ab7d06 |
|
|
|
ab7d06 |
Only afterwards the device is known in udev:
|
|
|
ab7d06 |
|
|
|
ab7d06 |
signal: link changed: 11: lbr0 <UP,LOWER_UP;broadcast,multicast,up,running,lowerup> mtu 1500 arp 1 bridge* init addrgenmode eui64 addr D2:A1:B4:17:18:F2 driver bridge
|
|
|
ab7d06 |
|
|
|
ab7d06 |
At this point, we also clear NM_UNMANAGED_PLATFORM_INIT, making
|
|
|
ab7d06 |
the device managed with reason NM_DEVICE_STATE_REASON_NOW_MANAGED.
|
|
|
ab7d06 |
That results in managing the external device.
|
|
|
ab7d06 |
|
|
|
ab7d06 |
Fix that by only clearing NM_UNMANAGED_EXTERNAL_DOWN after the device
|
|
|
ab7d06 |
is no longer NM_UNMANAGED_PLATFORM_INIT.
|
|
|
ab7d06 |
|
|
|
ab7d06 |
https://bugzilla.redhat.com/show_bug.cgi?id=1269199
|
|
|
ab7d06 |
|
|
|
ab7d06 |
(cherry picked from commit e29ab54335c6a5ef1ce6bac525f1f18a8e81b96e)
|
|
|
ab7d06 |
(cherry picked from commit cde15dda2e513517433e6273ca62e8b8c2c35ccb)
|
|
|
ab7d06 |
---
|
|
|
ab7d06 |
src/devices/nm-device.c | 44 ++++++++++++++++++++++++++------------------
|
|
|
ab7d06 |
1 file changed, 26 insertions(+), 18 deletions(-)
|
|
|
ab7d06 |
|
|
|
ab7d06 |
diff --git a/src/devices/nm-device.c b/src/devices/nm-device.c
|
|
|
ab7d06 |
index 83cd6e9..7c49f3f 100644
|
|
|
ab7d06 |
--- a/src/devices/nm-device.c
|
|
|
ab7d06 |
+++ b/src/devices/nm-device.c
|
|
|
ab7d06 |
@@ -1375,6 +1375,8 @@ device_link_changed (NMDevice *self)
|
|
|
ab7d06 |
NMPlatformLink info;
|
|
|
ab7d06 |
const NMPlatformLink *pllink;
|
|
|
ab7d06 |
int ifindex;
|
|
|
ab7d06 |
+ gboolean emit_link_initialized = FALSE;
|
|
|
ab7d06 |
+ gboolean was_up;
|
|
|
ab7d06 |
|
|
|
ab7d06 |
priv->device_link_changed_id = 0;
|
|
|
ab7d06 |
|
|
|
ab7d06 |
@@ -1450,8 +1452,29 @@ device_link_changed (NMDevice *self)
|
|
|
ab7d06 |
if (ip_ifname_changed)
|
|
|
ab7d06 |
update_dynamic_ip_setup (self);
|
|
|
ab7d06 |
|
|
|
ab7d06 |
- if (priv->up != NM_FLAGS_HAS (info.flags, IFF_UP)) {
|
|
|
ab7d06 |
- priv->up = NM_FLAGS_HAS (info.flags, IFF_UP);
|
|
|
ab7d06 |
+ if (priv->ifindex > 0 && !priv->platform_link_initialized && info.initialized) {
|
|
|
ab7d06 |
+ priv->platform_link_initialized = TRUE;
|
|
|
ab7d06 |
+
|
|
|
ab7d06 |
+ if (nm_platform_link_get_unmanaged (NM_PLATFORM_GET, priv->ifindex, &platform_unmanaged)) {
|
|
|
ab7d06 |
+ nm_device_set_unmanaged (self,
|
|
|
ab7d06 |
+ NM_UNMANAGED_DEFAULT,
|
|
|
ab7d06 |
+ platform_unmanaged,
|
|
|
ab7d06 |
+ NM_DEVICE_STATE_REASON_USER_REQUESTED);
|
|
|
ab7d06 |
+ }
|
|
|
ab7d06 |
+
|
|
|
ab7d06 |
+ nm_device_set_unmanaged (self,
|
|
|
ab7d06 |
+ NM_UNMANAGED_PLATFORM_INIT,
|
|
|
ab7d06 |
+ FALSE,
|
|
|
ab7d06 |
+ NM_DEVICE_STATE_REASON_NOW_MANAGED);
|
|
|
ab7d06 |
+
|
|
|
ab7d06 |
+ emit_link_initialized = TRUE;
|
|
|
ab7d06 |
+ }
|
|
|
ab7d06 |
+
|
|
|
ab7d06 |
+ was_up = priv->up;
|
|
|
ab7d06 |
+ priv->up = NM_FLAGS_HAS (info.flags, IFF_UP);
|
|
|
ab7d06 |
+
|
|
|
ab7d06 |
+ if ( priv->platform_link_initialized
|
|
|
ab7d06 |
+ && (emit_link_initialized || priv->up != was_up)) {
|
|
|
ab7d06 |
|
|
|
ab7d06 |
/* Manage externally-created software interfaces only when they are IFF_UP */
|
|
|
ab7d06 |
g_assert (priv->ifindex > 0);
|
|
|
ab7d06 |
@@ -1493,23 +1516,8 @@ device_link_changed (NMDevice *self)
|
|
|
ab7d06 |
}
|
|
|
ab7d06 |
}
|
|
|
ab7d06 |
|
|
|
ab7d06 |
- if (priv->ifindex > 0 && !priv->platform_link_initialized && info.initialized) {
|
|
|
ab7d06 |
- priv->platform_link_initialized = TRUE;
|
|
|
ab7d06 |
-
|
|
|
ab7d06 |
- if (nm_platform_link_get_unmanaged (NM_PLATFORM_GET, priv->ifindex, &platform_unmanaged)) {
|
|
|
ab7d06 |
- nm_device_set_unmanaged (self,
|
|
|
ab7d06 |
- NM_UNMANAGED_DEFAULT,
|
|
|
ab7d06 |
- platform_unmanaged,
|
|
|
ab7d06 |
- NM_DEVICE_STATE_REASON_USER_REQUESTED);
|
|
|
ab7d06 |
- }
|
|
|
ab7d06 |
-
|
|
|
ab7d06 |
- nm_device_set_unmanaged (self,
|
|
|
ab7d06 |
- NM_UNMANAGED_PLATFORM_INIT,
|
|
|
ab7d06 |
- FALSE,
|
|
|
ab7d06 |
- NM_DEVICE_STATE_REASON_NOW_MANAGED);
|
|
|
ab7d06 |
-
|
|
|
ab7d06 |
+ if (emit_link_initialized)
|
|
|
ab7d06 |
g_signal_emit (self, signals[LINK_INITIALIZED], 0);
|
|
|
ab7d06 |
- }
|
|
|
ab7d06 |
|
|
|
ab7d06 |
return G_SOURCE_REMOVE;
|
|
|
ab7d06 |
}
|
|
|
ab7d06 |
--
|
|
|
ab7d06 |
2.4.3
|
|
|
ab7d06 |
|